{"id":335184,"date":"2022-06-30T15:00:56","date_gmt":"2022-06-30T15:00:56","guid":{"rendered":"http:\/\/savepearlharbor.com\/?p=335184"},"modified":"-0001-11-30T00:00:00","modified_gmt":"-0001-11-29T21:00:00","slug":"","status":"publish","type":"post","link":"https:\/\/savepearlharbor.com\/?p=335184","title":{"rendered":"<span>\u0421\u043e\u0437\u0434\u0430\u043d\u0438\u0435 API \u0441 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u0435\u043c TDD \u0432 Laravel<\/span>"},"content":{"rendered":"<div><\/div>\n<div id=\"post-content-body\">\n<div>\n<div class=\"article-formatted-body article-formatted-body article-formatted-body_version-2\">\n<div xmlns=\"http:\/\/www.w3.org\/1999\/xhtml\">\n<figure class=\"full-width\"><img loading=\"lazy\" decoding=\"async\" src=\"https:\/\/habrastorage.org\/r\/w1560\/getpro\/habr\/upload_files\/073\/f3c\/b43\/073f3cb436767cd2ae4b58c06c0d2f2f.png\" width=\"780\" height=\"439\" data-src=\"https:\/\/habrastorage.org\/getpro\/habr\/upload_files\/073\/f3c\/b43\/073f3cb436767cd2ae4b58c06c0d2f2f.png\"\/><figcaption><\/figcaption><\/figure>\n<p>\u041f\u0440\u0438\u0432\u0435\u0442, <em>Artisans (\u0430\u043d\u0433\u043b. \u041c\u0430\u0441\u0442\u0435\u0440\u0430; \u043f\u0440\u043e\u0433\u0440. Artisan \u2014 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043a\u043e\u043c\u0430\u043d\u0434\u043d\u043e\u0439 \u0441\u0442\u0440\u043e\u043a\u0438, \u0432\u0445\u043e\u0434\u044f\u0449\u0438\u0439 \u0432 \u0441\u043e\u0441\u0442\u0430\u0432 Laravel)<\/em>, \u043c\u0435\u043d\u044f \u0437\u043e\u0432\u0443\u0442 <a href=\"https:\/\/alberto-rosas.dev\/\">\u0410\u043b\u044c\u0431\u0435\u0440\u0442\u043e \u0420\u043e\u0441\u0430\u0441<\/a> (Alberto Rosas), \u044f \u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0441\u044c Laravel \u0443\u0436\u0435 \u043c\u043d\u043e\u0433\u043e \u043b\u0435\u0442, \u0438 \u043e\u0434\u043d\u0430 \u0438\u0437 \u0441\u0430\u043c\u044b\u0445 \u043f\u043e\u043b\u0435\u0437\u043d\u044b\u0445 \u0438 \u0441\u0442\u043e\u044f\u0449\u0438\u0445 \u0432\u0435\u0449\u0435\u0439, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u044f \u0443\u0437\u043d\u0430\u043b, \u2014 \u044d\u0442\u043e \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u044b\u0445 \u0442\u0435\u0441\u0442\u043e\u0432\u044b\u0445 \u0441\u044c\u044e\u0442\u043e\u0432 \u0434\u043b\u044f \u0441\u0432\u043e\u0438\u0445 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439. \u041e\u0447\u0435\u043d\u044c \u043f\u0440\u0438\u044f\u0442\u043d\u043e \u0432\u0438\u0434\u0435\u0442\u044c, \u0447\u0442\u043e \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u0432\u0441\u0435 \u0447\u0430\u0449\u0435 \u043f\u0440\u0430\u043a\u0442\u0438\u043a\u0443\u0435\u0442\u0441\u044f \u0432 \u0441\u043e\u043e\u0431\u0449\u0435\u0441\u0442\u0432\u0435 Laravel, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0432 \u044d\u0442\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0435 \u043c\u044b \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u043e\u0441\u043d\u043e\u0432 TDD (Test Driven Development. \u0420\u0430\u0437\u0440\u0430\u0431\u043e\u0442\u043a\u0430 \u0447\u0435\u0440\u0435\u0437 \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435) \u0432 Laravel \u0438 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0442\u0435\u043c\u0443 \u0432 \u0434\u0440\u0443\u0433\u0438\u0445 \u0441\u0442\u0430\u0442\u044c\u044f\u0445.<\/p>\n<p>\u0412\u043e\u0442 \u0447\u0442\u043e \u043d\u0430\u043c \u043f\u0440\u0435\u0434\u0441\u0442\u043e\u0438\u0442 \u043e\u0441\u0432\u043e\u0438\u0442\u044c:<\/p>\n<ul>\n<li>\n<p>\u0421\u043e\u0437\u0434\u0430\u043d\u0438\u0435 API \u0441 \u043d\u0443\u043b\u044f \u0441 \u0443\u043f\u043e\u0440\u043e\u043c \u043d\u0430 \u0431\u0430\u0437\u043e\u0432\u044b\u0435 \u0444\u0438\u0447\u0438 <a href=\"https:\/\/www.codecademy.com\/articles\/what-is-crud\">CRUD<\/a>.<\/p>\n<\/li>\n<li>\n<p>\u0412\u043d\u0435\u0434\u0440\u0438\u043c <a href=\"https:\/\/medium.com\/@sameernyaupane\/php-test-driven-development-part-1-introduction-5483362d79b5\">TDD<\/a> \u0441 \u0441\u0430\u043c\u043e\u0433\u043e \u043d\u0430\u0447\u0430\u043b\u0430, \u0447\u0442\u043e\u0431\u044b \u043f\u0440\u043e\u0438\u043b\u043b\u044e\u0441\u0442\u0440\u0438\u0440\u043e\u0432\u0430\u0442\u044c, \u043a\u0430\u043a \u0441\u043e\u0437\u0434\u0430\u0432\u0430\u0442\u044c \u0442\u0435\u0441\u0442\u0438\u0440\u0443\u0435\u043c\u044b\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f Laravel.<\/p>\n<\/li>\n<\/ul>\n<h3>\u0412\u0432\u0435\u0434\u0435\u043d\u0438\u0435<\/h3>\n<p>\u0417\u0430\u0434\u0430\u0447\u0430 \u0434\u0430\u043d\u043d\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0438 \u2014 \u043f\u043e\u043a\u0430\u0437\u0430\u0442\u044c, \u0447\u0442\u043e TDD \u043d\u0435 \u043e\u0431\u044f\u0437\u0430\u0442\u0435\u043b\u044c\u043d\u043e \u0434\u043e\u043b\u0436\u0435\u043d \u0431\u044b\u0442\u044c \u0442\u0440\u0443\u0434\u043d\u044b\u043c \u0438\u043b\u0438 \u043c\u0443\u0447\u0438\u0442\u0435\u043b\u044c\u043d\u044b\u043c, \u0447\u0442\u043e\u0431\u044b \u0441\u0434\u0435\u043b\u0430\u0442\u044c \u0435\u0433\u043e \u0447\u0430\u0441\u0442\u044c\u044e \u0440\u0430\u0431\u043e\u0447\u0435\u0433\u043e \u043f\u0440\u043e\u0446\u0435\u0441\u0441\u0430 \u0434\u043b\u044f \u0432\u0430\u0441 \u0438\u043b\u0438 \u0432\u0430\u0448\u0435\u0439 \u043a\u043e\u043c\u0430\u043d\u0434\u044b. \u0412\u0430\u043c \u043f\u0440\u043e\u0441\u0442\u043e \u043d\u0443\u0436\u043d\u043e \u043f\u043e\u043d\u044f\u0442\u044c, \u0441 \u0447\u0435\u0433\u043e \u043d\u0430\u0447\u0430\u0442\u044c \u0438 \u0447\u0442\u043e \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c.<\/p>\n<p>\u041c\u043d\u0435 \u043d\u0435 \u043f\u043e\u0442\u0440\u0435\u0431\u043e\u0432\u0430\u043b\u043e\u0441\u044c \u043c\u043d\u043e\u0433\u043e \u0432\u0440\u0435\u043c\u0435\u043d\u0438, \u0447\u0442\u043e\u0431\u044b \u043f\u0440\u0435\u0432\u0440\u0430\u0442\u0438\u0442\u044c TDD \u0432 \u043f\u0440\u0438\u0432\u044b\u0447\u043a\u0443 \u0438 \u043d\u0430\u0439\u0442\u0438 \u043f\u043e\u0434\u0445\u043e\u0434\u044f\u0449\u0438\u0439 \u0434\u043b\u044f \u043c\u0435\u043d\u044f \u0440\u0430\u0431\u043e\u0447\u0438\u0439 \u043f\u0440\u043e\u0446\u0435\u0441\u0441. \u0412\u0430\u0436\u043d\u043e \u0438\u043c\u0435\u0442\u044c \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043d\u044b\u0439 \u0440\u0430\u0431\u043e\u0447\u0438\u0439 \u043f\u0440\u043e\u0446\u0435\u0441\u0441; \u0437\u043d\u0430\u043d\u0438\u0435 \u0442\u043e\u0433\u043e, \u0447\u0442\u043e \u0432\u044b \u0431\u0443\u0434\u0435\u0442\u0435 \u0434\u0435\u043b\u0430\u0442\u044c \u0432 \u043f\u0435\u0440\u0432\u0443\u044e \u043e\u0447\u0435\u0440\u0435\u0434\u044c \u0432 \u0442\u0438\u043f\u0438\u0447\u043d\u043e\u043c \u043f\u0440\u043e\u0435\u043a\u0442\u0435, \u043c\u043e\u0436\u0435\u0442 \u043f\u043e\u043c\u043e\u0447\u044c \u0432\u0430\u043c \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u0441\u0432\u043e\u044e \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u0443\u044e \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443, \u043e\u0440\u0433\u0430\u043d\u0438\u0437\u043e\u0432\u0430\u0442\u044c \u0432\u0441\u0435 \u0442\u0430\u043a\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c, \u0447\u0442\u043e\u0431\u044b \u0432\u044b \u0437\u043d\u0430\u043b\u0438, \u0433\u0434\u0435 \u0447\u0442\u043e \u043d\u0430\u0445\u043e\u0434\u0438\u0442\u0441\u044f \u0432 \u0432\u0430\u0448\u0435\u043c \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0438, \u0438 \u043d\u0435\u043c\u043d\u043e\u0433\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0438\u0437\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0432\u0430\u0448\u0438 \u043b\u0438\u0447\u043d\u044b\u0435\/\u043a\u043b\u0438\u0435\u043d\u0442\u0441\u043a\u0438\u0435 \u043f\u0440\u043e\u0435\u043a\u0442\u044b.<\/p>\n<p>\u0414\u0440\u0443\u0433\u0438\u043c\u0438 \u0441\u043b\u043e\u0432\u0430\u043c\u0438, TDD \u043f\u043e\u043c\u043e\u0433\u0430\u0435\u0442 \u0432\u0430\u043c \u043a\u043e\u0434\u0438\u0442\u044c \u0431\u044b\u0441\u0442\u0440\u0435\u0435 \u0438 \u0443\u0432\u0435\u0440\u0435\u043d\u043d\u0435\u0435. \u042f \u0443\u043f\u043e\u043c\u0438\u043d\u0430\u043b \u0440\u0430\u043d\u0435\u0435 \u043e \u043f\u043e\u043d\u0438\u043c\u0430\u043d\u0438\u0438 \u0442\u043e\u0433\u043e, \u0447\u0442\u043e \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0432 \u043f\u0435\u0440\u0432\u0443\u044e \u043e\u0447\u0435\u0440\u0435\u0434\u044c. \u041d\u043e \u043d\u0430 \u0441\u0430\u043c\u043e\u043c \u0434\u0435\u043b\u0435 \u044d\u0442\u043e \u043d\u0435 \u0438\u043c\u0435\u0435\u0442 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f, \u043c\u044b \u0441\u0430\u043c\u0438 \u043d\u0430\u043f\u0440\u0430\u0432\u0438\u043c \u0432\u0430\u0441 \u043a \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c \u0442\u0435\u0441\u0442\u0430\u043c, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0435\u0434\u0438\u043d\u0441\u0442\u0432\u0435\u043d\u043d\u043e\u0435, \u0447\u0442\u043e \u0432\u0430\u043c \u043d\u0443\u0436\u043d\u043e \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u0437\u043d\u0430\u0442\u044c, \u044d\u0442\u043e \u0444\u0438\u0447\u0430, \u043a\u043e\u0442\u043e\u0440\u0443\u044e \u0432\u044b \u0445\u043e\u0442\u0438\u0442\u0435 \u043f\u0440\u043e\u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c.<\/p>\n<h3>\u0422\u0440\u0435\u0431\u043e\u0432\u0430\u043d\u0438\u044f<\/h3>\n<ul>\n<li>\n<p>\u0411\u0430\u0437\u043e\u0432\u044b\u0435 \u0437\u043d\u0430\u043d\u0438\u044f \u043e \u0444\u0440\u0435\u0439\u043c\u0432\u043e\u0440\u043a\u0435.<\/p>\n<\/li>\n<li>\n<p>\u0421\u0432\u0435\u0436\u0438\u0439 \u043f\u0440\u043e\u0435\u043a\u0442 Laravel.<\/p>\n<\/li>\n<\/ul>\n<p>\u0412 \u043e\u0431\u0449\u0435\u043c, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0441\u0442\u043e \u043d\u0430\u0447\u043d\u0435\u043c.<\/p>\n<h3>\u041a\u043e\u043d\u0442\u0435\u043a\u0441\u0442<\/h3>\n<p>\u0412 \u044d\u0442\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0435 \u0438, \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e, \u0432 \u0441\u0435\u0440\u0438\u0438 \u0441\u0442\u0430\u0442\u0435\u0439 \u044f \u0431\u0443\u0434\u0443 \u0441\u043e\u0437\u0434\u0430\u0432\u0430\u0442\u044c API \u0434\u043b\u044f \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f \u043f\u043e \u043d\u0435\u0434\u0432\u0438\u0436\u0438\u043c\u043e\u0441\u0442\u0438.<\/p>\n<p>\u0422\u0430\u0431\u043b\u0438\u0446\u0430 <code>properties<\/code>:<\/p>\n<ul>\n<li>\n<p>id (\u0438\u0434\u0435\u043d\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440): \u043f\u0435\u0440\u0432\u0438\u0447\u043d\u044b\u0439 \u043a\u043b\u044e\u0447;<\/p>\n<\/li>\n<li>\n<p>type (\u0442\u0438\u043f): \u0441\u0442\u0440\u043e\u043a\u0430 (\u043f\u043e\u0437\u0436\u0435 \u043c\u044b, \u0432\u0435\u0440\u043e\u044f\u0442\u043d\u043e, \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u0441\u0432\u044f\u0437\u044c \u0441 &#8216;property_types&#8217;);<\/p>\n<\/li>\n<li>\n<p>price (\u0446\u0435\u043d\u0430): \u043f\u043e\u043b\u043e\u0436\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0435 \u0446\u0435\u043b\u043e\u0435 \u0447\u0438\u0441\u043b\u043e;<\/p>\n<\/li>\n<li>\n<p>description (\u043e\u043f\u0438\u0441\u0430\u043d\u0438\u0435): \u0442\u0435\u043a\u0441\u0442.<\/p>\n<\/li>\n<\/ul>\n<p>\u041f\u0440\u0438 \u0440\u0430\u0431\u043e\u0442\u0435 \u0441 Laravel \u043c\u044b \u043e\u0431\u044b\u0447\u043d\u043e \u0441\u043b\u0435\u0434\u0443\u0435\u043c \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443\/\u0441\u043e\u0433\u043b\u0430\u0448\u0435\u043d\u0438\u044e, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u043e\u0440\u0433\u0430\u043d\u0438\u0437\u0430\u0446\u0438\u0438 \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0439 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440\u0430 \u0432 5 \u043c\u0435\u0442\u043e\u0434\u0430\u0445 API:<\/p>\n<ul>\n<li>\n<p>index (\u0438\u043d\u0434\u0435\u043a\u0441);<\/p>\n<\/li>\n<li>\n<p>store (\u0445\u0440\u0430\u043d\u0435\u043d\u0438\u0435);<\/p>\n<\/li>\n<li>\n<p>update (\u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u0435);<\/p>\n<\/li>\n<li>\n<p>delete (\u0443\u0434\u0430\u043b\u0435\u043d\u0438\u0435).<\/p>\n<\/li>\n<\/ul>\n<p>\u041c\u044b \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e \u043f\u0440\u043e\u0440\u0430\u0431\u043e\u0442\u0430\u0435\u043c \u0432\u0435\u0441\u044c \u043d\u0430\u0448 \u0441\u043f\u0438\u0441\u043e\u043a \u0438 \u043e\u0431\u044a\u044f\u0441\u043d\u0438\u043c, \u043a\u0430\u043a\u0438\u0435 \u0432\u0435\u0449\u0438 \u043d\u0430\u0438\u0431\u043e\u043b\u0435\u0435 \u0438\u043d\u0442\u0435\u0440\u0435\u0441\u043d\u044b \u0434\u043b\u044f \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f.<\/p>\n<h3>\u0422\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 Index<\/h3>\n<p>\u041c\u0435\u0442\u043e\u0434 Index \u043e\u0431\u044b\u0447\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f \u0434\u043b\u044f \u0432\u043e\u0437\u0432\u0440\u0430\u0442\u0430 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043d\u043e\u0439 <a href=\"https:\/\/laravel.com\/docs\/8.x\/collections\">\u041a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u0438<\/a> \u0434\u043b\u044f \u041c\u043e\u0434\u0435\u043b\u0438.<\/p>\n<h3>\u041f\u0440\u043e\u0432\u0435\u0434\u0435\u043c \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435:<\/h3>\n<ul>\n<li>\n<p>\u0423 \u043d\u0430\u0441 \u0435\u0441\u0442\u044c \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0439 \u044d\u043d\u0434\u043f\u043e\u0439\u043d\u0442 API \u0434\u043b\u044f \u043f\u043e\u043b\u0443\u0447\u0435\u043d\u0438\u044f \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u0438 \u0440\u0435\u0441\u0443\u0440\u0441\u043e\u0432.<\/p>\n<\/li>\n<li>\n<p>\u041f\u0440\u043e\u0432\u0435\u0440\u0438\u043c, \u0447\u0442\u043e \u043e\u0442\u0432\u0435\u0442 \u043f\u0440\u0438\u0445\u043e\u0434\u0438\u0442 \u0432 \u0432\u0438\u0434\u0435 \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u0438.<\/p>\n<\/li>\n<\/ul>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u0442\u0435\u0441\u0442\u0430, \u043e\u0442\u043a\u0440\u043e\u0435\u043c \u0442\u0435\u0440\u043c\u0438\u043d\u0430\u043b \u0432\u043d\u0443\u0442\u0440\u0438 \u0432\u0430\u0448\u0435\u0433\u043e \u043f\u0440\u043e\u0435\u043a\u0442\u0430 Laravel \u0438 \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0435\u0433\u043e:<\/p>\n<pre><code>php artisan make:test Api\/PropertiesTest<\/code><\/pre>\n<p>\u042d\u0442\u043e \u0441\u043e\u0437\u0434\u0430\u0441\u0442 \u0444\u0430\u0439\u043b \u0442\u0435\u0441\u0442\u0430 \u0432 <code>\/tests\/Features\/Api\/PropertiesTest.php<\/code><\/p>\n<p>\u0412\u043d\u0443\u0442\u0440\u0438 \u044d\u0442\u043e\u0433\u043e \u0444\u0430\u0439\u043b\u0430 \u043c\u044b \u0434\u043e\u0431\u0430\u0432\u0438\u043c \u043d\u0430\u0448 \u043f\u0435\u0440\u0432\u044b\u0439 \u0442\u0435\u0441\u0442, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0442\u044c, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043f\u0430\u043b\u0438 \u0432 \u043c\u0430\u0440\u0448\u0440\u0443\u0442 API <code>index<\/code> \u0438 \u043f\u043e\u043b\u0443\u0447\u0438\u043b\u0438 \u043e\u0431\u0440\u0430\u0442\u043d\u043e \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u044e \u0441\u0432\u043e\u0439\u0441\u0442\u0432 (Properties), \u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u043d\u0430 \u0434\u0430\u043d\u043d\u044b\u0439 \u043c\u043e\u043c\u0435\u043d\u0442 \u0443 \u043d\u0430\u0441 \u043d\u0435\u0442, \u043d\u043e \u044f \u043f\u043e\u0437\u0432\u043e\u043b\u044e \u0442\u0435\u0441\u0442\u0443 \u0441\u0430\u043c\u043e\u043c\u0443 \u043f\u043e\u0440\u0443\u043b\u0438\u0442\u044c.<\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Feature\\Api;      use Tests\\TestCase; use Illuminate\\Foundation\\Testing\\RefreshDatabase;      class PropertiesTest extends TestCase   { use RefreshDatabase;  \/** @test *\/ public function can_get_all_properties() { \/\/ Create Property so that the response returns it. $property = Property::factory()->create();  $response = $this->getJson(route('api.properties.index')); \/\/ We will only assert that the response returns a 200 status for now. $response->assertOk();  } }<\/code><\/pre>\n<p>\u041a\u043e\u043d\u0435\u0447\u043d\u043e, \u0437\u0434\u0435\u0441\u044c \u0432\u043e\u0437\u043d\u0438\u043a\u043d\u0435\u0442 \u043e\u0448\u0438\u0431\u043a\u0430, \u043c\u044b \u0435\u0449\u0435 \u043d\u0435 \u0441\u043e\u0437\u0434\u0430\u043b\u0438 \u043c\u043e\u0434\u0435\u043b\u044c <code>Property<\/code>, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043f\u043e\u0441\u043b\u0435 \u0437\u0430\u043f\u0443\u0441\u043a\u0430 <code>.\/vendor\/bin\/phpunit --testdox<\/code> \u0432 \u043a\u0430\u0442\u0430\u043b\u043e\u0433\u0435 \u043d\u0430\u0448\u0435\u0433\u043e \u043f\u0440\u043e\u0435\u043a\u0442\u0430 \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u043c:<\/p>\n<pre><code class=\"php\">Tests\\Feature\\Api\\PropertiesTest::can_get_all_properties Error: Class 'Tests\\Feature\\Api\\Property' not found<\/code><\/pre>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e:<\/p>\n<p><code>php artisan make:model Property -mf<\/code><\/p>\n<p>\u041f\u0440\u0438\u0432\u0435\u0434\u0435\u043d\u043d\u0430\u044f \u0432\u044b\u0448\u0435 \u043a\u043e\u043c\u0430\u043d\u0434\u0430 \u0432\u044b\u043f\u043e\u043b\u043d\u0438\u0442:<\/p>\n<ul>\n<li>\n<p>\u0421\u043e\u0437\u0434\u0430\u0441\u0442 \u043c\u043e\u0434\u0435\u043b\u044c, \u0440\u0430\u0441\u043f\u043e\u043b\u043e\u0436\u0435\u043d\u043d\u0443\u044e \u0432 <code>app\/Models\/Property.php<\/code><\/p>\n<\/li>\n<li>\n<p><code>-m<\/code> \u0441\u043e\u0437\u0434\u0430\u0441\u0442 \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u044e \u0432 <code>\/database\/migrations\/<\/code><\/p>\n<\/li>\n<li>\n<p><code>-f<\/code> \u0441\u043e\u0437\u0434\u0430\u0441\u0442 \u043a\u043b\u0430\u0441\u0441 Factory (\u0444\u0430\u0431\u0440\u0438\u043a\u0430) \u0432 <code>\/database\/factories\/PropertyFactory<\/code>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043c\u044b \u0431\u0443\u0434\u0435\u043c \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0434\u043b\u044f \u043c\u043e\u043a\u0438\u043d\u0433\u0430 &#171;Property&#187; \u0438 \u0435\u0433\u043e \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u043e\u0432.<\/p>\n<\/li>\n<\/ul>\n<p>\u041f\u0440\u0438\u043c\u0435\u043d\u044f\u044f TDD, \u0434\u0435\u0439\u0441\u0442\u0432\u0443\u0435\u043c \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e; \u043f\u043e\u0441\u043b\u0435 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u043d\u0430\u0448\u0435\u0439 \u043c\u043e\u0434\u0435\u043b\u0438, \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u0438 \u0438 \u0444\u0430\u0431\u0440\u0438\u043a\u0438 \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0442\u0435\u0441\u0442 \u0441\u043d\u043e\u0432\u0430 (\u0432\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u0442\u0435 \u0442\u0443 \u0436\u0435 \u043e\u0448\u0438\u0431\u043a\u0443, \u0435\u0441\u043b\u0438 \u043d\u0435 \u0438\u043c\u043f\u043e\u0440\u0442\u0438\u0440\u0443\u0435\u0442\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u043c\u043e\u0434\u0435\u043b\u0438 Property \u043f\u043e\u0432\u0435\u0440\u0445 \u0432\u0430\u0448\u0435\u0433\u043e \u0442\u0435\u0441\u0442\u0430):<\/p>\n<pre><code>Tests\\Feature\\Api\\PropertiesTest::can_get_all_properties Symfony\\Component\\Routing\\Exception\\RouteNotFoundException:  Route [api.properties.index] not defined.<\/code><\/pre>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0438 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u044b\u0439 \u044d\u043d\u0434\u043f\u043e\u0439\u043d\u0442 \u0432 \u0444\u0430\u0439\u043b\u0435 <code>\/routes\/api.php<\/code>:<\/p>\n<pre><code class=\"php\">use App\\Http\\Controllers\\Api\\PropertyController;  Route::get( 'properties',  [PropertyController::class, 'index'] )->name('api.properties.index');<\/code><\/pre>\n<p>\u0414\u0430\u043b\u0435\u0435 \u043c\u044b \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0435\u0433\u043e \u0438 \u043f\u043e\u043b\u0443\u0447\u0438\u043c \u043e\u0448\u0438\u0431\u043a\u0443; <code>PropertyController<\/code> \u043d\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442:<\/p>\n<p><code>ReflectionException: Class PropertyController does not exist<\/code><\/p>\n<p>\u041e\u0442\u043a\u0440\u043e\u0435\u043c \u0442\u0435\u0440\u043c\u0438\u043d\u0430\u043b \u0438 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u043d\u0430\u0448 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440 \u0447\u0435\u0440\u0435\u0437 artisan:<\/p>\n<pre><code>php artisan make:controller Api\/PropertyController<\/code><\/pre>\n<p>\u041a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440 \u0431\u0443\u0434\u0435\u0442 \u0440\u0430\u0441\u043f\u043e\u043b\u043e\u0436\u0435\u043d \u0432 <code>\/app\/Http\/Controllers\/Api\/PropertyController.php<\/code> .<\/p>\n<p>\u041e\u0442\u043a\u0440\u043e\u0439\u0442\u0435 \u0440\u0430\u043d\u0435\u0435 \u0441\u043e\u0437\u0434\u0430\u043d\u043d\u044b\u0439 \u0444\u0430\u0439\u043b \u0438 \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u0435 \u0442\u0435\u0441\u0442 \u0441\u043d\u043e\u0432\u0430:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use Illuminate\\Http\\Request;   use App\\Http\\Controllers\\Controller;      class PropertyController extends Controller   {       }<\/code><\/pre>\n<p>\u041c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0435\u0449\u0435 \u043e\u0434\u043d\u0443 \u043e\u0448\u0438\u0431\u043a\u0443, \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u044e\u0449\u0443\u044e \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u043c\u0435\u0442\u043e\u0434 <code>index<\/code> \u043d\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u0435\u0433\u043e, \u0447\u0442\u043e\u0431\u044b, \u043d\u0430\u043a\u043e\u043d\u0435\u0446, \u0434\u043e\u0431\u0438\u0442\u044c\u0441\u044f \u043f\u0440\u043e\u0445\u043e\u0436\u0434\u0435\u043d\u0438\u044f \u0442\u0435\u0441\u0442\u0430:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use Illuminate\\Http\\Request;   use App\\Http\\Controllers\\Controller;      class PropertyController extends Controller   {   public function index() { } }<\/code><\/pre>\n<p>\u0417\u0430\u043f\u0443\u0441\u043a\u0430\u0435\u043c \u0442\u0435\u0441\u0442, \u0438 \u043e\u043d \u043f\u0440\u043e\u0445\u043e\u0434\u0438\u0442, \u043d\u043e&#8230; \u043c\u044b \u043d\u0435 \u0432\u044b\u043f\u043e\u043b\u043d\u0438\u043b\u0438 \u0444\u0430\u043a\u0442\u0438\u0447\u0435\u0441\u043a\u0443\u044e \u043b\u043e\u0433\u0438\u043a\u0443, \u0447\u0442\u043e\u0431\u044b \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c, \u0447\u0442\u043e \u043e\u043d \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u044e, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e, \u043e\u0431\u043d\u043e\u0432\u0438\u0432 \u043d\u0430\u0448 \u0442\u0435\u0441\u0442, \u0447\u0442\u043e\u0431\u044b \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u0442\u044c, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c JSON.<\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Feature\\Api;      use Tests\\TestCase; use Illuminate\\Foundation\\Testing\\RefreshDatabase;      class PropertiesTest extends TestCase   { use RefreshDatabase;  \/** @test *\/ public function can_get_all_properties() { \/\/ Create Property so that the response returns it. $property = Property::factory()->create();  $response = $this->getJson(route('api.properties.index')); \/\/ We will only assert that the response returns a 200  \/\/ status for now. $response->assertOk();   \/\/ Add the assertion that will prove that we receive what we need  \/\/ from the response. $response->assertJson([ 'data' => [ [ 'id' => $property->id, 'type' => $property->type,   'price' => $property->price,   'description' => $property->description, ] ] ]); } }<\/code><\/pre>\n<p>\u0418, \u043a\u043e\u043d\u0435\u0447\u043d\u043e \u0436\u0435, \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c:<\/p>\n<p><code>Invalid JSON was returned from the route<\/code><strong>.<\/strong> (\u0441 \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0430 \u0431\u044b\u043b \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0435\u043d \u043d\u0435\u0434\u043e\u043f\u0443\u0441\u0442\u0438\u043c\u044b\u0439 JSON), \u043d\u0443&#8230; \u043c\u044b \u043d\u0430 \u0441\u0430\u043c\u043e\u043c \u0434\u0435\u043b\u0435 \u043d\u0438\u0447\u0435\u0433\u043e \u043d\u0435 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c \u0438\u0437 \u043c\u0435\u0442\u043e\u0434\u0430 <code>index<\/code>, \u0442\u0430\u043a \u0447\u0442\u043e \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use App\\Models\\Property; use Illuminate\\Http\\Request;   use App\\Http\\Controllers\\Controller;      class PropertyController extends Controller   {   public function index() { return response()->json([       'data' => Property::all()   ]); } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u0447\u0438\u043d\u0430, \u043f\u043e \u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u043c\u044b \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c \u043c\u0430\u0441\u0441\u0438\u0432 <code>data<\/code> \u0438 \u0432\u043d\u0443\u0442\u0440\u0438 \u043d\u0435\u0433\u043e \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u044e, \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0435 \u043e\u0442\u0432\u0435\u0442\u043e\u0432 API, \u0433\u0434\u0435 \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u043c\u043e\u0435 \u0434\u043e\u043b\u0436\u043d\u043e \u0431\u044b\u0442\u044c \u0432\u043d\u0443\u0442\u0440\u0438 \u044d\u0442\u043e\u0433\u043e \u043c\u0430\u0441\u0441\u0438\u0432\u0430 <code>data<\/code>.<\/p>\n<p>\u041c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0435\u0449\u0435 \u043e\u0434\u043d\u0443 \u043e\u0448\u0438\u0431\u043a\u0443, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u0438, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b Property, \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0435\u043d\u043d\u044b\u0435 \u0438\u0437 \u043e\u0442\u0432\u0435\u0442\u0430, \u043d\u043e \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b \u044f\u0432\u043b\u044f\u044e\u0442\u0441\u044f <code>null<\/code>, \u043c\u043e\u0436\u0435\u0442\u0435 \u0441\u0435\u0431\u0435 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u0438\u0442\u044c, \u043f\u043e\u0447\u0435\u043c\u0443?<\/p>\n<pre><code class=\"php\">Unable to find JSON:   [{     \"data\": [         {             \"id\": 1,             \"type\": null,             \"price\": null,             \"description\": null         }     ] }]  within response JSON:  [{     \"data\": [         {             \"id\": 1,             \"created_at\": \"2021-10-15T14:44:21.000000Z\",             \"updated_at\": \"2021-10-15T14:44:21.000000Z\"         }     ] }]<\/code><\/pre>\n<p>\u0412\u044b \u0443\u0433\u0430\u0434\u0430\u043b\u0438! \u041c\u044b \u043d\u0435 \u043e\u0431\u043d\u043e\u0432\u0438\u043b\u0438 \u043d\u0430\u0448 \u043a\u043b\u0430\u0441\u0441 PropertyFactory, \u0447\u0442\u043e\u0431\u044b \u043e\u043d \u0438\u043c\u0435\u043b \u0437\u0430\u043f\u043b\u0430\u043d\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \u043d\u0430\u043c\u0438 \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b:<\/p>\n<pre><code class=\"php\">use App\\Models\\Property;   use Illuminate\\Database\\Eloquent\\Factories\\Factory;  class PropertyFactory extends Factory   {    \/**    * The name of the factory's corresponding model. * * @var string    *\/    protected $model = Property::class;     \/**    * Define the model's default state.       * @return array    *\/    public function definition()    {  return [   'type' => $this->faker->word,   'price' => $this->faker->randomNumber(6),   'description' => $this->faker->paragraph,  ];    }  }<\/code><\/pre>\n<p>\u041c\u044b \u043d\u0430\u0447\u043d\u0435\u043c \u043f\u043e\u043b\u0443\u0447\u0430\u0442\u044c \u043e\u0448\u0438\u0431\u043a\u0438, \u0441\u0432\u044f\u0437\u0430\u043d\u043d\u044b\u0435 \u0441 &#171;\u043d\u0435\u0438\u0437\u0432\u0435\u0441\u0442\u043d\u044b\u043c\u0438 \u0441\u0442\u043e\u043b\u0431\u0446\u0430\u043c\u0438&#8230;&#187;. \u043f\u043e\u0442\u043e\u043c\u0443 \u0447\u0442\u043e \u043d\u0430\u0448\u0430 \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u044f \u043d\u0435 \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442 \u0441\u0442\u043e\u043b\u0431\u0446\u043e\u0432, \u043a\u043e\u0442\u043e\u0440\u044b\u0435, \u043f\u043e \u043d\u0430\u0448\u0435\u043c\u0443 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u044e, \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0442.<\/p>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043e\u0431\u043d\u043e\u0432\u0438\u043c \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u044e, \u0434\u043e\u0431\u0430\u0432\u0438\u0432 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u044b\u0435 \u0441\u0442\u043e\u043b\u0431\u0446\u044b:<\/p>\n<pre><code class=\"php\">Schema::create('properties', function (Blueprint $table) {   $table->id();   $table->string('type', 20); $table->unsignedInteger('price'); $table->text('description'); $table->timestamps();   });<\/code><\/pre>\n<p>\u0415\u0441\u043b\u0438 \u043c\u044b \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0442\u0435\u0441\u0442 \u0441\u043d\u043e\u0432\u0430, \u0442\u043e \u0437\u0430\u043c\u0435\u0442\u0438\u043c, \u0447\u0442\u043e \u043e\u043d \u0441\u043d\u043e\u0432\u0430 \u043f\u0440\u043e\u0448\u0435\u043b, \u0438 \u043d\u0430 \u044d\u0442\u043e\u0442 \u0440\u0430\u0437 \u043e\u043a\u043e\u043d\u0447\u0430\u0442\u0435\u043b\u044c\u043d\u043e.<\/p>\n<p>\u0422\u0435\u043f\u0435\u0440\u044c, \u043a\u043e\u0433\u0434\u0430 \u043c\u044b \u0441\u043e\u0437\u0434\u0430\u043b\u0438 \u043f\u0440\u043e\u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0439 \u043c\u0435\u0442\u043e\u0434 <code>index<\/code>, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0441 \u043c\u0435\u0442\u043e\u0434\u043e\u043c Store, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043f\u043e\u0442\u0440\u0435\u0431\u0443\u0435\u0442 \u043d\u0435\u043c\u043d\u043e\u0433\u043e \u0431\u043e\u043b\u044c\u0448\u0435 \u0440\u0430\u0431\u043e\u0442\u044b.<\/p>\n<h3>\u0422\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043c\u0435\u0442\u043e\u0434\u0430 Store<\/h3>\n<p>\u042d\u0442\u043e\u0442 \u0442\u0435\u0441\u0442 \u043c\u044b \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u0432\u0442\u043e\u0440\u043e\u0433\u043e \u0442\u0435\u0441\u0442\u0430 \u0432 \u0442\u043e\u043c \u0436\u0435 \u0444\u0430\u0439\u043b\u0435 <code>tests\/Feature\/Api\/PropertiesTest.php<\/code><\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Feature\\Api;      use Tests\\TestCase; use Illuminate\\Foundation\\Testing\\RefreshDatabase;      class PropertiesTest extends TestCase   { use RefreshDatabase;  \/** @test *\/   public function can_get_all_properties(){...}  \/** @test *\/ \/** @test *\/     public function can_store_a_property()     {         \/\/ Build a non-persisted Property factory model.         $newProperty = Property::factory()->make();          $response = $this->postJson(             route('api.properties.store'),             $newProperty->toArray()         );         \/\/ We assert that we get back a status 201:         \/\/ Resource Created for now.         $response->assertCreated();         \/\/ Assert that at least one column gets returned from the response         \/\/ in the format we need .         $response->assertJson([              'data' => ['type' => $newProperty->type]          ]);         \/\/ Assert the table properties contains the factory we made.         $this->assertDatabaseHas(              'properties',               $newProperty->toArray()          );     } }<\/code><\/pre>\n<p>\u0412\u043d\u0430\u0447\u0430\u043b\u0435 \u043a\u0440\u0430\u0442\u043a\u043e \u0440\u0435\u0437\u044e\u043c\u0438\u0440\u0443\u0435\u043c \u044d\u0442\u043e\u0442 \u0442\u0435\u0441\u0442:<\/p>\n<ul>\n<li>\n<p>\u041c\u044b \u0441\u043e\u0437\u0434\u0430\u0435\u043c \u043d\u0435\u043f\u0435\u0440\u0441\u0438\u0441\u0442\u0435\u043d\u0442\u043d\u0443\u044e \u043c\u043e\u0434\u0435\u043b\u044c Property \u0434\u043b\u044f \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f \u0432 \u043a\u0430\u0447\u0435\u0441\u0442\u0432\u0435 \u0437\u0430\u043f\u0440\u043e\u0441\u0430 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043c\u0435\u0442\u043e\u0434\u0430 Factory (\u0444\u0430\u0431\u0440\u0438\u043a\u0430): <code>make<\/code>.<\/p>\n<\/li>\n<li>\n<p>\u041c\u044b \u0434\u0435\u043b\u0430\u0435\u043c post-\u0437\u0430\u043f\u0440\u043e\u0441 \u0447\u0435\u0440\u0435\u0437 API \u043a \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0443 <code>route('api.properties.store')<\/code> \u0441 \u0434\u0430\u043d\u043d\u044b\u043c\u0438 \u0437\u0430\u043f\u0440\u043e\u0441\u0430.<\/p>\n<\/li>\n<li>\n<p>\u0417\u0430\u0442\u0435\u043c \u043f\u043e\u0434\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u0435\u043c, \u0447\u0442\u043e \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0432 \u043e\u0442\u0432\u0435\u0442 \u0441\u0442\u0430\u0442\u0443\u0441-\u043a\u043e\u0434 <code>201: Resource Created<\/code> (\u0420\u0435\u0441\u0443\u0440\u0441 \u0441\u043e\u0437\u0434\u0430\u043d)<\/p>\n<\/li>\n<li>\n<p>\u0423\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u0435\u043c, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u043b\u0438 \u0445\u043e\u0442\u044f \u0431\u044b \u043e\u0434\u0438\u043d \u0438\u0437 \u043d\u043e\u0432\u044b\u0445 \u043a\u043b\u044e\u0447\u0435\u0439, \u0447\u0442\u043e\u0431\u044b \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c, \u0447\u0442\u043e \u043e\u043d \u043f\u0440\u0438\u0448\u0435\u043b \u0432 \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u043e\u043c \u0444\u043e\u0440\u043c\u0430\u0442\u0435.<\/p>\n<\/li>\n<li>\n<p>\u0418, \u043d\u0430\u043a\u043e\u043d\u0435\u0446, \u043c\u044b \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u0435\u043c, \u0447\u0442\u043e \u0442\u0430\u0431\u043b\u0438\u0446\u0430 <code>properties<\/code> \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442 \u043d\u043e\u0432\u0443\u044e \u043c\u043e\u0434\u0435\u043b\u044c Property.<\/p>\n<\/li>\n<\/ul>\n<p>\u0417\u0430\u043f\u0443\u0441\u0442\u0438\u0432 \u0442\u0435\u0441\u0442, \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u043e\u0448\u0438\u0431\u043a\u0443:<\/p>\n<pre><code>Symfony\\Component\\Routing\\Exception\\RouteNotFoundException : Route [api.properties.store] not defined.<\/code><\/pre>\n<p>\u0427\u0442\u043e \u043e\u0437\u043d\u0430\u0447\u0430\u0435\u0442 \u0438\u043c\u0435\u043d\u043d\u043e \u044d\u0442\u043e; \u043d\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442 \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0430 API \u0441 \u0438\u043c\u0435\u043d\u0435\u043c, \u043f\u043e\u0434\u043e\u0431\u043d\u044b\u043c \u0432\u044b\u0448\u0435\u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u043c\u0443 \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0443.<\/p>\n<p>\u0412 <code>\/routes\/api.php<\/code>:<\/p>\n<pre><code class=\"php\">Route::post( 'properties',  [PropertyController::class, 'store'] )->name('api.properties.store');<\/code><\/pre>\n<p>\u041a\u043e\u043d\u0435\u0447\u043d\u043e, \u043c\u044b \u043d\u0435 \u0441\u043e\u0437\u0434\u0430\u043b\u0438 \u043c\u0435\u0442\u043e\u0434 <code>store<\/code>, \u043c\u044b \u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use App\\Models\\Property;   use Illuminate\\Http\\Request;   use Illuminate\\Http\\JsonResponse;   use App\\Http\\Controllers\\Controller;      class PropertyController extends Controller   {   public function index() : JsonResponse {...}    public function store(Request $request)   {  return response()->json([ 'data' => Property::create($request->all()) ], 201);  } }<\/code><\/pre>\n<p>\u042d\u0442\u043e \u0444\u0430\u043a\u0442\u0438\u0447\u0435\u0441\u043a\u0438 \u0435\u0434\u0438\u043d\u0441\u0442\u0432\u0435\u043d\u043d\u043e\u0435, \u0447\u0442\u043e \u043d\u0430\u043c \u043d\u0430\u0434\u043e \u0441\u0434\u0435\u043b\u0430\u0442\u044c. \u041d\u043e \u043d\u0430\u0448\u0430 \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0430\u044f \u043e\u0448\u0438\u0431\u043a\u0430 \u0441\u0432\u044f\u0437\u0430\u043d\u0430 \u0441 <a href=\"https:\/\/laravel.com\/docs\/8.x\/eloquent#mass-assignment\">Mass Assignment<\/a> (\u043c\u0430\u0441\u0441\u043e\u0432\u043e\u0435 \u043d\u0430\u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435), \u0438 \u043f\u043e \u0441\u0443\u0442\u0438 \u043d\u0430\u043c \u043d\u0443\u0436\u043d\u043e \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u0441\u0432\u043e\u0439\u0441\u0442\u0432\u043e <code>protected $fillable = [];<\/code>, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442 \u0438\u043c\u0435\u043d\u0430 \u0441\u0442\u043e\u043b\u0431\u0446\u043e\u0432, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0432\u044b \u0445\u043e\u0442\u0438\u0442\u0435 \u043c\u0430\u0441\u0441\u043e\u0432\u043e \u043f\u0440\u0438\u0441\u0432\u043e\u0438\u0442\u044c. \u041e\u043d\u043e \u0432\u044b\u0433\u043b\u044f\u0434\u0438\u0442 \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Models;      use Illuminate\\Database\\Eloquent\\Model;   use Illuminate\\Database\\Eloquent\\Factories\\HasFactory;      class Property extends Model   {    use HasFactory;       protected $fillable = ['type', 'price', 'description'];   }<\/code><\/pre>\n<p>\u041e\u0442\u043b\u0438\u0447\u043d\u043e, \u0442\u0435\u043f\u0435\u0440\u044c \u043c\u044b \u0432 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0435 \u043f\u043e\u043b\u0443\u0447\u0438\u043b\u0438 \u0437\u0435\u043b\u0435\u043d\u044b\u0439. \u041a\u043e\u043d\u0435\u0447\u043d\u043e, \u043d\u0430\u043c \u0432\u0441\u0435 \u0435\u0449\u0435 \u043d\u0443\u0436\u043d\u043e \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c \u044d\u0442\u0438 \u0441\u0432\u043e\u0439\u0441\u0442\u0432\u0430 \u043f\u0440\u0438 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u0438, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u043e.<\/p>\n<p>\u041d\u0430\u0447\u043d\u0443 \u0441 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f &#171;\u042e\u043d\u0438\u0442&#187; \u0442\u0435\u0441\u0442\u0430 (\u0438\u043b\u0438 \u0442\u0430\u043a \u044f \u0435\u0433\u043e \u043d\u0430\u0437\u0432\u0430\u043b), \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043c\u0435\u043d\u044f \u0438\u043d\u0442\u0435\u0440\u0435\u0441\u0443\u0435\u0442 \u0442\u043e\u043b\u044c\u043a\u043e \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u0435, \u0447\u0442\u043e \u044f \u043f\u043e\u043b\u0443\u0447\u0430\u044e \u043e\u0448\u0438\u0431\u043a\u0443 \u0432 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0435 &#171;\u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f&#187; \u0438\u043b\u0438 &#171;\u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u044f&#187; Property \u0438 \u043d\u0430\u043c\u0435\u0440\u0435\u043d\u043d\u043e \u0434\u0435\u043b\u0430\u044e \u0438\u0445 \u043d\u0435\u0443\u0434\u0430\u0447\u043d\u044b\u043c\u0438; \u0442\u0430\u043a\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c \u0432\u044b \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0435\u0442\u0435, \u0447\u0442\u043e <a href=\"https:\/\/laravel.com\/docs\/8.x\/validation#form-request-validation\">FormRequest<\/a> \u0432\u043d\u0435\u0434\u0440\u044f\u0435\u0442\u0441\u044f \u0432 \u043c\u0435\u0442\u043e\u0434\u044b <code>store<\/code> \u0438 <code>update<\/code> \u0432 \u0432\u0430\u0448\u0435\u043c \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440\u0435.<\/p>\n<p>\u0421\u043e\u0437\u0434\u0430\u043d\u0438\u0435 FormRequest \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e artisan \u0432\u044b\u0433\u043b\u044f\u0434\u0438\u0442 \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c:<\/p>\n<pre><code>php artisan make:request PropertyRequest<\/code><\/pre>\n<p>\u0412 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0435 \u0431\u0443\u0434\u0435\u0442 \u0441\u043e\u0437\u0434\u0430\u043d \u0444\u0430\u0439\u043b <code>\/app\/Http\/Requests\/PropertyRequest.php<\/code>, \u043e\u0442\u043a\u0440\u043e\u0439\u0442\u0435 \u0435\u0433\u043e \u0438 \u0432\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u0442\u0435 \u044d\u0442\u043e\u0442 \u043a\u043b\u0430\u0441\u0441:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Requests;      use Illuminate\\Foundation\\Http\\FormRequest;      class PropertyRequest extends FormRequest   {    public function authorize()    {   \/\/ Change this to: true  return false;    }      public function rules()    {   return [    \/\/    ];    }  }<\/code><\/pre>\n<p>\u0417\u0434\u0435\u0441\u044c \u0432\u044b \u0437\u0430\u043c\u0435\u0442\u0438\u0442\u0435 \u043c\u0435\u0442\u043e\u0434 \u043f\u043e\u0434 \u043d\u0430\u0437\u0432\u0430\u043d\u0438\u0435\u043c <code>authorize<\/code>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 <code>false<\/code>, \u0432\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c \u0434\u043e\u0441\u0442\u0443\u043f \u043a \u043c\u0435\u0442\u043e\u0434\u0443, \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044f true\/false, \u043a\u043e\u0433\u0434\u0430 \u0443\u0441\u0442\u0430\u043d\u043e\u0432\u043b\u0435\u043d\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043d\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e; \u0435\u0441\u043b\u0438 \u043e\u043d\u043e \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 false, \u043c\u0435\u0442\u043e\u0434 \u0432 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440\u0435 \u0432\u0435\u0440\u043d\u0435\u0442 \u043a\u043e\u0434 \u0441\u043e\u0441\u0442\u043e\u044f\u043d\u0438\u044f 403: unauthorized.<\/p>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0438 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u043d\u0430\u0448 <code>PropertyRequestTest<\/code> \u0434\u043b\u044f \u043f\u0440\u043e\u0432\u0435\u0440\u043a\u0438 \u043f\u0440\u0430\u0432\u0438\u043b, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043c\u044b \u043f\u0440\u0438\u043c\u0435\u043d\u044f\u0435\u043c \u043a \u043d\u0430\u0448\u0435\u043c\u0443 \u043c\u0435\u0442\u043e\u0434\u0443 <code>store<\/code> \u0438, \u0432\u043f\u043e\u0441\u043b\u0435\u0434\u0441\u0442\u0432\u0438\u0438, \u0438 \u043a <code>update<\/code>.<\/p>\n<pre><code>php artisan make:test Http\/Requests\/PropertyRequestTest --unit<\/code><\/pre>\n<p>\u042f \u043e\u0431\u044b\u0447\u043d\u043e \u0440\u0430\u0437\u043c\u0435\u0449\u0430\u044e \u0441\u0432\u043e\u0438 \u0442\u0435\u0441\u0442\u044b \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438 \u0432 <code>tests\/Unit\/Http\/Requests\/<\/code>, \u0447\u0442\u043e\u0431\u044b \u0441\u044b\u043c\u0438\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0440\u0430\u0441\u043f\u043e\u043b\u043e\u0436\u0435\u043d\u0438\u0435 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440\u0430, \u0433\u0434\u0435 \u043e\u043d \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f. \u041e\u0442\u043a\u0440\u043e\u0439\u0442\u0435 \u043d\u043e\u0432\u044b\u0439 \u0442\u0435\u0441\u0442:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Unit\\Http\\Requests;      use Tests\\TestCase;    class PropertyRequestTest extends TestCase   {   }<\/code><\/pre>\n<p>\u0415\u0441\u043b\u0438 \u0437\u0430\u043c\u0435\u0442\u0438\u043b\u0438, \u0442\u043e \u044f \u0438\u0437\u043c\u0435\u043d\u0438\u043b \u043e\u0434\u043d\u0443 \u0434\u0435\u0442\u0430\u043b\u044c, \u043f\u0440\u0435\u0436\u0434\u0435 \u0447\u0435\u043c \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u0442\u044c, \u0438 \u044d\u0442\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 <code>TestCase<\/code>, \u0438\u043c\u043f\u043e\u0440\u0442\u0438\u0440\u0443\u0435\u043c\u043e\u0435 \u043f\u043e \u0443\u043c\u043e\u043b\u0447\u0430\u043d\u0438\u044e. \u041e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435<strong> <\/strong><code>PHPUnit\\Framework\\TestCase<\/code> \u0432\u0445\u043e\u0434\u0438\u0442 \u043f\u043e \u0443\u043c\u043e\u043b\u0447\u0430\u043d\u0438\u044e \u0432 \u043c\u043e\u0434\u0443\u043b\u044c\u043d\u044b\u0435 \u0442\u0435\u0441\u0442\u044b \u0438 \u044f\u0432\u043b\u044f\u0435\u0442\u0441\u044f\u00a0 \u043f\u043e \u0443\u043c\u043e\u043b\u0447\u0430\u043d\u0438\u044e \u043a\u043b\u0430\u0441\u0441\u043e\u043c <a href=\"https:\/\/phpunit.de\/\">PHPUnit<\/a>, \u043d\u0430\u043c \u043d\u0443\u0436\u043d\u043e \u0437\u0430\u043c\u0435\u043d\u0438\u0442\u044c \u0435\u0433\u043e \u043d\u0430 Laravel&#8217;s TestCase, \u0440\u0430\u0441\u043f\u043e\u043b\u043e\u0436\u0435\u043d\u043d\u044b\u0439 \u0432 \u043a\u0430\u0442\u0430\u043b\u043e\u0433\u0435 <code>tests<\/code>, \u0447\u0442\u043e\u0431\u044b \u0438\u043c\u0435\u0442\u044c \u0432 \u0441\u0432\u043e\u0435\u043c \u0440\u0430\u0441\u043f\u043e\u0440\u044f\u0436\u0435\u043d\u0438\u0438 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u044f \u0438 \u0445\u0435\u043b\u043f\u0435\u0440\u044b Laravel.<\/p>\n<p>\u0418\u0442\u0430\u043a, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u043f\u0435\u0440\u0432\u043e\u0433\u043e \u0442\u0435\u0441\u0442\u0430, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0435\u0442, \u0432\u044b\u043f\u043e\u043b\u043d\u044f\u0435\u043c \u043b\u0438 \u043c\u044b \u043f\u0440\u0430\u0432\u0438\u043b\u043e <code>required<\/code>:<\/p>\n<pre><code class=\"php\">use RefreshDatabase;      private string $routePrefix = 'api.properties.';      \/**    * @test    * @throws \\Throwable    *\/   public function type_is_required()   {    $validatedField = 'type';    $brokenRule = null;      $property = Property::factory()->make([    $validatedField => $brokenRule    ]);     $this->postJson(    route($this->routePrefix . 'store'),    $property->toArray()    )->assertJsonValidationErrors($validatedField);   }<\/code><\/pre>\n<p>\u0418\u0442\u0430\u043a, \u044d\u0442\u043e \u043c\u043e\u0439 \u0441\u043f\u043e\u0441\u043e\u0431 \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0438\u0437\u0430\u0446\u0438\u0438 \u0442\u0435\u0441\u0442\u043e\u0432 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438. \u041c\u044b \u0441\u043e\u0437\u0434\u0430\u0435\u043c \u043e\u0431\u0449\u0438\u0439 \u0441\u043f\u043e\u0441\u043e\u0431 \u0440\u0435\u043f\u043b\u0438\u043a\u0430\u0446\u0438\u0438 \u043f\u0440\u0430\u0432\u0438\u043b \u0438 \u043f\u0440\u043e\u0441\u0442\u043e \u043e\u0431\u043d\u043e\u0432\u043b\u044f\u0435\u043c \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u0443\u044e <code>$brokenRule<\/code>, \u0447\u0442\u043e\u0431\u044b \u043e\u043d\u0430 \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u043b\u0430 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043d\u0430\u0440\u0443\u0448\u0438\u0442 \u043f\u0440\u0430\u0432\u0438\u043b\u043e. \u041f\u043e\u044d\u0442\u043e\u043c\u0443 \u043c\u043e\u0436\u043d\u043e \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u0442\u044c, \u0447\u0442\u043e \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u044b JSON-\u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438 \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0442 \u043e\u0448\u0438\u0431\u043a\u0443. \u0422\u0430\u043a\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c, \u044f \u043c\u043e\u0433\u0443 \u043f\u0440\u043e\u0441\u0442\u043e \u043a\u043e\u043f\u0438\u043f\u0430\u0441\u0442\u0438\u0442\u044c \u0442\u043e\u0442 \u0436\u0435 \u0442\u0435\u0441\u0442 \u0438 \u0442\u043e\u043b\u044c\u043a\u043e \u0438\u0437\u043c\u0435\u043d\u0438\u0442\u044c <code>$validatedField<\/code> \u0438 <code>$brokenRule<\/code> \u0434\u043b\u044f \u043d\u043e\u0432\u043e\u0439 \u043f\u0440\u043e\u0432\u0435\u0440\u043a\u0438.<\/p>\n<p>\u0412\u043e\u0442 \u0447\u0442\u043e \u0437\u0434\u0435\u0441\u044c \u043f\u0440\u043e\u0438\u0441\u0445\u043e\u0434\u0438\u0442:<\/p>\n<ul>\n<li>\n<p>\u0421\u043d\u0430\u0447\u0430\u043b\u0430 \u043c\u044b \u0441\u043e\u0437\u0434\u0430\u0435\u043c \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u0443\u044e \u0432\u0430\u043b\u0438\u0434\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u043e\u0433\u043e \u043f\u043e\u043b\u044f, \u0447\u0442\u043e\u0431\u044b \u043f\u043e\u0432\u0442\u043e\u0440\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0438\u043c\u044f \u0441\u0442\u043e\u043b\u0431\u0446\u0430 \u0438 \u0437\u0430\u043c\u0435\u043d\u044f\u0442\u044c \u0435\u0433\u043e \u0432 \u0434\u0440\u0443\u0433\u0438\u0445 \u0442\u0435\u0441\u0442\u0430\u0445.<\/p>\n<\/li>\n<li>\n<p>\u041c\u044b \u0441\u043e\u0437\u0434\u0430\u043b\u0438 \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u0443\u044e \u043d\u0430\u0440\u0443\u0448\u0435\u043d\u043d\u043e\u0433\u043e \u043f\u0440\u0430\u0432\u0438\u043b\u0430, \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0449\u0443\u044e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0431\u0443\u0434\u0435\u0442 \u0438\u043d\u0438\u0446\u0438\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0437\u0430\u043f\u0440\u043e\u0441 \u0444\u043e\u0440\u043c\u044b.<\/p>\n<\/li>\n<li>\n<p>\u0417\u0430\u0442\u0435\u043c \u043c\u044b \u0441\u043e\u0437\u0434\u0430\u0435\u043c \u043d\u0435\u043f\u0435\u0440\u0441\u0438\u0441\u0442\u0435\u043d\u0442\u043d\u0443\u044e \u043c\u043e\u0434\u0435\u043b\u044c \u0441\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f\u043c\u0438, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043d\u0430\u0440\u0443\u0448\u0430\u0442 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u044e.<\/p>\n<\/li>\n<li>\n<p>\u041c\u044b \u0434\u0435\u043b\u0430\u0435\u043c POST-\u0437\u0430\u043f\u0440\u043e\u0441, \u0447\u0442\u043e\u0431\u044b \u043f\u043e\u043f\u044b\u0442\u0430\u0442\u044c\u0441\u044f \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u043d\u043e\u0432\u043e\u0435 Property (\u0441\u0432\u043e\u0439\u0441\u0442\u0432\u043e).<\/p>\n<\/li>\n<li>\n<p>\u041c\u044b \u0441\u0440\u0430\u0437\u0443 \u0436\u0435 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u0435\u043c, \u0447\u0442\u043e \u043f\u0430\u043a\u0435\u0442 \u043e\u0448\u0438\u0431\u043e\u043a JSON-\u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438 \u0432\u043a\u043b\u044e\u0447\u0430\u0435\u0442 \u0432 \u0441\u0435\u0431\u044f \u043f\u0440\u043e\u0432\u0435\u0440\u0435\u043d\u043d\u043e\u0435 \u043f\u043e\u043b\u0435, \u043f\u043e\u0434\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u044f \u043d\u0430\u043b\u0438\u0447\u0438\u0435 \u043e\u0448\u0438\u0431\u043a\u0438, \u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e, \u043d\u0430\u0448 \u0437\u0430\u043f\u0440\u043e\u0441 \u0432\u044b\u043f\u043e\u043b\u043d\u044f\u0435\u0442 \u0441\u0432\u043e\u044e \u0440\u0430\u0431\u043e\u0442\u0443.<\/p>\n<\/li>\n<\/ul>\n<p>\u041f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u043e\u0448\u0438\u0431\u043a\u0443 \u043f\u043e\u0441\u043b\u0435 \u0432\u044b\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u044f \u0442\u0435\u0441\u0442\u0430:<\/p>\n<pre><code>Failed to find a validation error in the response for key: 'type'<\/code><\/pre>\n<p>\u042d\u0442\u043e \u043e\u0437\u043d\u0430\u0447\u0430\u0435\u0442, \u0447\u0442\u043e \u0442\u0435\u0441\u0442 \u043d\u0435 \u043e\u0431\u043d\u0430\u0440\u0443\u0436\u0438\u043b \u043e\u0448\u0438\u0431\u043a\u0443 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438 \u0432 \u043e\u0442\u0432\u0435\u0442\u0435 POST-\u0437\u0430\u043f\u0440\u043e\u0441\u0430, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043c\u044b \u0441\u0434\u0435\u043b\u0430\u043b\u0438, \u043e\u0447\u0435\u0432\u0438\u0434\u043d\u043e, \u0447\u0442\u043e \u043c\u044b \u043d\u0435 \u0438\u043c\u043f\u043b\u0435\u043c\u0435\u043d\u0442\u0438\u0440\u043e\u0432\u0430\u043b\u0438 FormRequest \u0432 <code>PropertyController<\/code>, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u043e\u043c\u0435\u043d\u044f\u0435\u043c <code>Illuminate\\Http\\Request<\/code> \u043d\u0430 \u043d\u0430\u0448 <code>PropertyRequest<\/code>, \u0447\u0442\u043e\u0431\u044b \u043c\u0435\u0442\u043e\u0434 <code>store<\/code> \u0432\u044b\u0433\u043b\u044f\u0434\u0435\u043b \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c:<\/p>\n<pre><code>public function store(PropertyRequest $request) : JsonResponse {...}<\/code><\/pre>\n<p>\u0415\u0441\u043b\u0438 \u043c\u044b \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0442\u0435\u0441\u0442, \u0442\u043e \u043f\u043e\u043b\u0443\u0447\u0438\u043c \u0442\u0443 \u0436\u0435 \u043e\u0448\u0438\u0431\u043a\u0443, \u043d\u043e \u0432 \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u043e\u043d\u0430 \u043d\u0435\u043a\u043e\u0440\u0440\u0435\u043a\u0442\u043d\u0430, \u044f \u043e\u0431\u044a\u044f\u0441\u043d\u044e \u044d\u0442\u043e \u0447\u0435\u0440\u0435\u0437 \u0441\u0435\u043a\u0443\u043d\u0434\u0443. \u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0435\u0440\u0435\u0439\u0434\u0435\u043c \u043a \u043d\u0430\u0448\u0435\u043c\u0443 \u0442\u0435\u0441\u0442\u0443 <code>type_is_required<\/code> \u0438 \u0434\u043e\u0431\u0430\u0432\u0438\u043c \u043c\u0435\u0442\u043e\u0434 \u043f\u043e\u0434 \u043d\u0430\u0437\u0432\u0430\u043d\u0438\u0435\u043c <code>withoutExceptionHandling<\/code>, \u043a\u0430\u043a \u043f\u043e\u043a\u0430\u0437\u0430\u043d\u043e \u043d\u0438\u0436\u0435:<\/p>\n<pre><code class=\"php\">\/**    * @test    * @throws \\Throwable    *\/   public function type_is_required()   {    $this->withoutExceptionHandling();  ...  }<\/code><\/pre>\n<p>\u041f\u043e \u0443\u043c\u043e\u043b\u0447\u0430\u043d\u0438\u044e Laravel \u0437\u0430\u0449\u0438\u0449\u0430\u0435\u0442 \u043d\u0430\u0441 \u043e\u0442 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u0438\u0441\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0439, \u043c\u043e\u0434\u0438\u0444\u0438\u0446\u0438\u0440\u0443\u044f \u043e\u0442\u0432\u0435\u0442 \u043d\u0430 &#171;\u0434\u0440\u0443\u0436\u0435\u0441\u0442\u0432\u0435\u043d\u043d\u043e\u0435&#187; \u0441\u043e\u043e\u0431\u0449\u0435\u043d\u0438\u0435 \u043e \u0442\u0430\u043a\u043e\u0439 \u043e\u0448\u0438\u0431\u043a\u0435. \u0412 \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u043d\u0430\u0448 \u0442\u0435\u0441\u0442 \u043d\u0435 \u0440\u0430\u0431\u043e\u0442\u0430\u0435\u0442, \u043f\u043e\u0442\u043e\u043c\u0443 \u0447\u0442\u043e \u043c\u044b \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u043b\u0438 <code>PropertyRequest<\/code>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442 \u043c\u0435\u0442\u043e\u0434 <code>authorize<\/code>, \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044e\u0449\u0438\u0439 <code>false<\/code>. \u042d\u0442\u043e\u0442 \u043c\u0435\u0442\u043e\u0434 \u043c\u043e\u0436\u0435\u0442 \u0431\u044b\u0442\u044c \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d \u0434\u043b\u044f \u0438\u043c\u043f\u043b\u0435\u043c\u0435\u043d\u0442\u0430\u0446\u0438\u0438 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438 \u043d\u0430 \u043f\u0440\u0430\u0432\u0430, \u0440\u043e\u043b\u0438 \u0438\u043b\u0438 \u0434\u0440\u0443\u0433\u043e\u0435 \u0443\u0441\u043b\u043e\u0432\u0438\u0435, \u043a\u043e\u0442\u043e\u0440\u043e\u0435, \u0432 \u0441\u043b\u0443\u0447\u0430\u0435 <code>true<\/code>, \u043f\u043e\u0437\u0432\u043e\u043b\u044f\u0435\u0442 \u0437\u0430\u043f\u0440\u043e\u0441\u0443 \u043f\u0435\u0440\u0435\u0439\u0442\u0438 \u043a \u043f\u0440\u0430\u0432\u0438\u043b\u0430\u043c \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438, \u0435\u0441\u043b\u0438 \u043d\u0435\u0442, \u0442\u043e \u043e\u043d \u0432\u044b\u0431\u0440\u0430\u0441\u044b\u0432\u0430\u0435\u0442 \u043a\u043e\u0434 \u0441\u043e\u0441\u0442\u043e\u044f\u043d\u0438\u044f 403, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 <code>unauthorized<\/code>, \u043a\u0430\u043a \u043e\u043f\u0438\u0441\u0430\u043d\u043e \u0440\u0430\u043d\u0435\u0435.<\/p>\n<p>\u0427\u0442\u043e\u0431\u044b \u0438\u0441\u043f\u0440\u0430\u0432\u0438\u0442\u044c \u044d\u0442\u043e, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0438\u0437\u043c\u0435\u043d\u0438\u043c <code>false<\/code> \u043d\u0430 <code>true<\/code>, \u0442\u0430\u043a \u043a\u0430\u043a \u043c\u044b \u043d\u0435 \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0435\u043c \u0437\u0434\u0435\u0441\u044c \u043d\u0438\u043a\u0430\u043a\u0438\u0445 \u043f\u0440\u0430\u0432 \u0438\u043b\u0438 \u0443\u0441\u043b\u043e\u0432\u0438\u0439:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Requests;      use Illuminate\\Foundation\\Http\\FormRequest;      class PropertyRequest extends FormRequest   {    \/**    * Determine if the user is authorized to make this request. * * @return bool    *\/    public function authorize()    {   return true;     }    ...<\/code><\/pre>\n<p>\u041f\u043e\u0441\u043b\u0435 \u044d\u0442\u043e\u0433\u043e \u043c\u044b \u0434\u043e\u043b\u0436\u043d\u044b \u0443\u0434\u0430\u043b\u0438\u0442\u044c \u043d\u0430\u0448 \u043c\u0435\u0442\u043e\u0434 <code>withoutExceptionHandling<\/code>, \u0447\u0442\u043e\u0431\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u0442\u044c \u043e\u0436\u0438\u0434\u0430\u0435\u043c\u043e\u0435 \u0441\u043e\u043e\u0431\u0449\u0435\u043d\u0438\u0435 \u043e\u0431 \u0438\u0441\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0438, \u0430 \u0437\u0430\u0442\u0435\u043c \u043d\u0430\u0447\u043d\u0435\u043c \u0434\u043e\u0431\u0430\u0432\u043b\u044f\u0442\u044c \u043f\u0440\u0430\u0432\u0438\u043b\u0430, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043c\u044b \u0442\u0435\u0441\u0442\u0438\u0440\u0443\u0435\u043c \u0432 \u043d\u0430\u0448\u0435\u0439 FormRequest.<\/p>\n<p>\u041f\u0435\u0440\u0432\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438 \u2014 <code>required<\/code>, \u0438 \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043c\u044b \u0442\u0435\u0441\u0442\u0438\u0440\u0443\u0435\u043c \u043a\u043e\u043b\u043e\u043d\u043a\u0443 <code>type<\/code>, \u044d\u0442\u043e \u0431\u0443\u0434\u0435\u0442 \u043d\u0430\u0448\u0430 \u043f\u0435\u0440\u0432\u0430\u044f \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u044f:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Requests;      use Illuminate\\Foundation\\Http\\FormRequest;      class PropertyRequest extends FormRequest   {    public function authorize()    {   return true;    }      public function rules()    {   return [      'type' => ['required'],  ];    }  }<\/code><\/pre>\n<p>\u0422\u0435\u043f\u0435\u0440\u044c, \u0435\u0441\u043b\u0438 \u043c\u044b \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0442\u0435\u0441\u0442, \u0442\u043e \u0432 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0435 \u043f\u043e\u043b\u0443\u0447\u0438\u043c \u0437\u0435\u043b\u0435\u043d\u044b\u0439, \u0438 \u043d\u0430\u0448 \u0442\u0435\u0441\u0442 \u043f\u0440\u043e\u0445\u043e\u0434\u0438\u0442, \u043f\u043e\u0434\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u044f \u044d\u0442\u043e:<\/p>\n<ul>\n<li>\n<p>\u041c\u0435\u0442\u043e\u0434 <code>store<\/code> \u0442\u0440\u0435\u0431\u0443\u0435\u0442, \u0447\u0442\u043e\u0431\u044b \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 <code>type<\/code> \u043f\u0440\u0438\u0441\u0443\u0442\u0441\u0442\u0432\u043e\u0432\u0430\u043b\u043e \u0432 \u0437\u0430\u043f\u0440\u043e\u0441\u0435.<\/p>\n<\/li>\n<li>\n<p>\u0412 \u043d\u0430\u0448\u0435\u043c \u043c\u0435\u0442\u043e\u0434\u0435 <code>store<\/code> \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f FormRequest.<\/p>\n<\/li>\n<li>\n<p>\u041c\u044b \u043d\u0435\u043c\u043d\u043e\u0433\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0438\u0437\u0438\u0440\u043e\u0432\u0430\u043b\u0438 \u043d\u0430\u0448 \u0442\u0435\u0441\u0442 \u043f\u0440\u043e\u0432\u0435\u0440\u043a\u0438, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u0439 \u043d\u0430\u0431\u043e\u0440 \u0442\u0435\u0441\u0442\u043e\u0432 \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0449\u0435 \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u0442\u044c.<\/p>\n<\/li>\n<\/ul>\n<p>\u0422\u0435\u043f\u0435\u0440\u044c \u044f \u043f\u0440\u043e\u0441\u0442\u043e \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e \u0434\u043e\u0431\u0430\u0432\u043b\u044e \u043e\u0441\u0442\u0430\u043b\u044c\u043d\u044b\u0435 \u0442\u0435\u0441\u0442\u044b, \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u0438\u0445 \u0440\u0435\u0430\u043b\u0438\u0437\u0430\u0446\u0438\u044f \u043e\u0447\u0435\u043d\u044c \u043f\u043e\u0445\u043e\u0436\u0430; \u043f\u043e\u0441\u043b\u0435 \u044d\u0442\u043e\u0433\u043e \u044f \u043f\u043e\u043a\u0430\u0436\u0443 \u0438 \u043e\u0431\u044a\u044f\u0441\u043d\u044e \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438, \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \u0432 FormRequest.<\/p>\n<p>\u041f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043c\u044b \u0443\u043a\u0430\u0437\u0430\u043b\u0438 \u0434\u043b\u0438\u043d\u0443 \u0441\u0442\u043e\u043b\u0431\u0446\u0430 <code>type<\/code> \u043c\u0430\u043a\u0441\u0438\u043c\u0443\u043c 20 \u0441\u0438\u043c\u0432\u043e\u043b\u043e\u0432, \u044f \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0443 \u0438 \u0434\u043e\u0431\u0430\u0432\u043b\u044e \u0442\u0443 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u044e.<\/p>\n<pre><code class=\"php\">\/**    * @test    * @throws \\Throwable    *\/   public function type_is_required() {...}   \/**    * @test    *\/   public function type_must_not_exceed_20_characters()   {    $validatedField = 'type';    $brokenRule = Str::random(21);      $property = Property::factory()->make([    $validatedField => $brokenRule    ]);     $this->postJson(    route($this->routePrefix . 'store'),    $property->toArray()    )->assertJsonValidationErrors($validatedField);   }<\/code><\/pre>\n<p>\u041a\u0430\u043a \u0432\u0438\u0434\u0438\u0442\u0435, \u043c\u044b \u0441\u0434\u0435\u043b\u0430\u043b\u0438 \u043a\u043e\u043f\u0438\u043f\u0430\u0441\u0442 \u043f\u0440\u0435\u0434\u044b\u0434\u0443\u0449\u0435\u0433\u043e \u0442\u0435\u0441\u0442\u0430 \u0438 \u0438\u0437\u043c\u0435\u043d\u0438\u043b\u0438 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 <code>$brokenRule<\/code> \u043d\u0430 \u0442\u043e, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043f\u0440\u0438\u0432\u0435\u0434\u0435\u0442 \u043a \u0441\u0431\u043e\u044e, \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u0438\u043c\u0435\u043d\u043d\u043e \u044d\u0442\u043e \u043d\u0430\u043c \u0438 \u043d\u0443\u0436\u043d\u043e. <code>$brokenRule<\/code> \u0441\u0442\u0430\u043d\u043e\u0432\u0438\u0442\u0441\u044f \u0441\u0442\u0440\u043e\u043a\u043e\u0439 \u0441\u043b\u0443\u0447\u0430\u0439\u043d\u044b\u0445 \u0431\u0443\u043a\u0432, \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0449\u0435\u0439 21 \u0441\u0438\u043c\u0432\u043e\u043b, \u0447\u0442\u043e \u0432\u044b\u0437\u044b\u0432\u0430\u0435\u0442 \u043e\u0448\u0438\u0431\u043a\u0443 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438. \u041f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043c\u044b \u043d\u0435 \u0434\u043e\u0431\u0430\u0432\u0438\u043b\u0438 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0432 FormRequest, \u0442\u0435\u0441\u0442 \u0435\u0449\u0435 \u043d\u0435 \u043f\u0440\u043e\u0439\u0434\u0435\u043d.<\/p>\n<pre><code class=\"php\">public function rules()   {    return [    'type' => ['required', 'max:20']    ];  }<\/code><\/pre>\n<p>\u041c\u044b \u0434\u043e\u0431\u0430\u0432\u043b\u044f\u0435\u043c \u043f\u0440\u0430\u0432\u0438\u043b\u043e <code>max<\/code>, \u0447\u0442\u043e\u0431\u044b \u0443\u043a\u0430\u0437\u0430\u0442\u044c \u043c\u0430\u043a\u0441\u0438\u043c\u0430\u043b\u044c\u043d\u043e\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043c\u044b \u043e\u0436\u0438\u0434\u0430\u0435\u043c \u043e\u0442 \u043f\u043e\u043b\u044f (\u043e\u043d\u043e \u0432 \u0434\u0430\u043d\u043d\u043e\u043c \u0441\u043b\u0443\u0447\u0430\u0435 \u0440\u0430\u0432\u043d\u043e 20), \u0438 \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0437\u0435\u043b\u0435\u043d\u044b\u0439!<\/p>\n<p>\u041f\u0435\u0440\u0435\u0445\u043e\u0434\u0438\u043c \u043a \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0435\u043c\u0443 \u0442\u0435\u0441\u0442\u0443, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043f\u0440\u0435\u0434\u043d\u0430\u0437\u043d\u0430\u0447\u0435\u043d \u0434\u043b\u044f <code>price<\/code>. \u041f\u0440\u043e\u0441\u0442\u043e \u0441\u043a\u043e\u043f\u0438\u0440\u0443\u0435\u043c \u043f\u0440\u0435\u0434\u044b\u0434\u0443\u0449\u0438\u0435 \u0442\u0435\u0441\u0442\u044b \u0438 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c:<\/p>\n<pre><code class=\"php\">\/**    * @test    * @throws \\Throwable    *\/   public function price_is_required()   {    $validatedField = 'price';    $brokenRule = null;      $property = Property::factory()->make([    $validatedField => $brokenRule    ]);    $this->postJson(    route($this->routePrefix . 'store'),    $property->toArray()    )->assertJsonValidationErrors($validatedField);   }<\/code><\/pre>\n<p>\u041c\u044b \u043f\u0440\u043e\u0441\u0442\u043e \u0438\u0437\u043c\u0435\u043d\u0438\u043b\u0438 \u043d\u0430\u0437\u0432\u0430\u043d\u0438\u0435 \u0442\u0435\u0441\u0442\u0430, \u0441\u043e\u043f\u0440\u043e\u0432\u043e\u0436\u0434\u0430\u0435\u043c\u043e\u0433\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435\u043c <code>$validatedField<\/code>, \u0432 \u0432\u0438\u0434\u0435 \u0441\u0442\u043e\u043b\u0431\u0446\u0430, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043c\u044b \u0432\u0430\u043b\u0438\u0434\u0438\u0440\u0443\u0435\u043c. \u041a\u0430\u043a \u0432\u0438\u0434\u0438\u0442\u0435, \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u044f \u043f\u0440\u0435\u0432\u0440\u0430\u0442\u0438\u043b\u0430\u0441\u044c \u0432 \u043b\u0451\u0433\u043a\u0443\u044e \u0437\u0430\u0434\u0430\u0447\u0443, \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043c\u044b \u043f\u0440\u043e\u0441\u0442\u043e \u043a\u043e\u043f\u0438\u043f\u0430\u0441\u0442\u0438\u043c \u043d\u0430\u0448\u0438 \u043f\u0440\u0435\u0434\u044b\u0434\u0443\u0449\u0438\u0435 \u0442\u0435\u0441\u0442\u044b.<\/p>\n<p>\u0414\u043e\u0431\u0430\u0432\u043b\u044f\u0435\u043c \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0434\u043b\u044f Price (\u0446\u0435\u043d\u0430):<\/p>\n<pre><code class=\"php\">public function rules()   {    return [    'type' => ['required', 'max:20'], 'price' => ['required'],  ];  }<\/code><\/pre>\n<p>\u0422\u0435\u0441\u0442\u044b \u043f\u0440\u043e\u0439\u0434\u0443\u0442, \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u0440\u0430\u0431\u043e\u0442\u0430 \u0443\u0436\u0435 \u0441\u0434\u0435\u043b\u0430\u043d\u0430. \u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0441\u0442\u043e \u0431\u044b\u0441\u0442\u0440\u043e \u0432\u044b\u043f\u043e\u043b\u043d\u0438\u043c \u043d\u0435\u0434\u043e\u0441\u0442\u0430\u044e\u0449\u0438\u0435 \u0442\u0435\u0441\u0442\u044b:<\/p>\n<pre><code class=\"php\">\/**    * @test    * @throws \\Throwable    *\/   public function price_must_be_an_integer()   {    $validatedField = 'price';    $brokenRule = 'not-integer';      $property = Property::factory()->make([    $validatedField => $brokenRule    ]);     $this->postJson(    route($this->routePrefix . 'store'),    $property->toArray()    )->assertJsonValidationErrors($validatedField);   }<\/code><\/pre>\n<p>\u041f\u0440\u0430\u0432\u0438\u043b\u043e \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438:<\/p>\n<pre><code class=\"php\">public function rules()   {    return [    'type' => ['required', 'max:20'],    'price' => ['required', 'integer'],    ]; }<\/code><\/pre>\n<p>\u0412 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0435 \u2014 \u0437\u0435\u043b\u0435\u043d\u044b\u0439. \u041c\u044b \u043c\u043e\u0433\u043b\u0438 \u0431\u044b \u0434\u0430\u0436\u0435 \u0438\u0437\u0431\u0435\u0436\u0430\u0442\u044c \u044d\u0442\u043e\u0433\u043e \u0442\u0435\u0441\u0442\u0430, \u0434\u043e\u0431\u0430\u0432\u0438\u0432 <a href=\"https:\/\/laravel.com\/docs\/8.x\/eloquent-mutators#attribute-casting\">Attribute<u> <\/u>Casting<\/a> (\u043a\u0430\u0441\u0442\u0438\u043d\u0433 \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u043e\u0432) \u0434\u043b\u044f \u0441\u0442\u043e\u043b\u0431\u0446\u0430 <code>price<\/code> \u043a\u0430\u043a <code>integer<\/code>, \u043d\u043e \u044f \u043f\u0440\u0435\u0434\u043f\u043e\u0447\u0438\u0442\u0430\u044e \u043f\u043e\u043a\u0430 \u0434\u0435\u0440\u0436\u0430\u0442\u044c \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438 \u0432\u043c\u0435\u0441\u0442\u0435.<\/p>\n<p>\u041f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043f\u043e\u043b\u0435 <code>description<\/code> \u044f\u0432\u043b\u044f\u0435\u0442\u0441\u044f \u0442\u0438\u043f\u043e\u043c \u0441\u0442\u043e\u043b\u0431\u0446\u0430 <code>text<\/code>, \u044f \u043d\u0435 \u0443\u0432\u0435\u0440\u0435\u043d, \u0447\u0442\u043e \u043d\u0430\u043c \u043d\u0443\u0436\u043d\u043e \u044d\u0442\u043e \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0442\u044c, \u0442\u0430\u043a \u043a\u0430\u043a \u043f\u043e\u043b\u0435 <code>text<\/code> \u043c\u043e\u0436\u0435\u0442 \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0442\u044c \u0434\u043e <strong>65,535<\/strong> \u0431\u0430\u0439\u0442, \u0447\u0442\u043e \u0432\u043f\u043e\u043b\u043d\u0435 \u0434\u043e\u0441\u0442\u0430\u0442\u043e\u0447\u043d\u043e \u0434\u043b\u044f \u0442\u043e\u0433\u043e, \u0447\u0442\u043e\u0431\u044b \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c \u043c\u043e\u0433 \u043d\u0430\u0431\u0440\u0430\u0442\u044c \u0432\u0441\u0435, \u0447\u0442\u043e \u0437\u0430\u0445\u043e\u0447\u0435\u0442.<\/p>\n<p>\u041d\u0430 \u044d\u0442\u043e\u043c \u043d\u0430\u0448 \u043c\u0435\u0442\u043e\u0434 <code>store<\/code> \u043f\u0440\u043e\u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d \u0432\u043c\u0435\u0441\u0442\u0435 \u0441 \u0435\u0433\u043e \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0435\u0439. \u0423\u0432\u0438\u0434\u0438\u043c\u0441\u044f \u0432 \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0435\u043c \u0442\u0435\u0441\u0442\u0435.<\/p>\n<h3>\u0422\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043c\u0435\u0442\u043e\u0434\u0430 Update<\/h3>\n<p>\u041c\u044b \u043f\u0440\u043e\u0448\u043b\u0438 \u043f\u043e\u043b\u043e\u0432\u0438\u043d\u0443 \u043f\u0443\u0442\u0438. \u041f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0441 \u043c\u0435\u0442\u043e\u0434\u043e\u043c Update.<\/p>\n<p>\u041a\u0430\u043a \u0432\u0438\u0434\u043d\u043e \u0438\u0437 \u043f\u0440\u0435\u0434\u044b\u0434\u0443\u0449\u0438\u0445 \u0442\u0435\u0441\u0442\u043e\u0432, \u0447\u0435\u0440\u0435\u0437 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0432\u0440\u0435\u043c\u044f \u0432\u0441\u0435 \u0441\u0442\u0430\u043d\u043e\u0432\u0438\u0442\u0441\u044f \u0434\u043e\u0432\u043e\u043b\u044c\u043d\u043e \u043f\u0440\u043e\u0441\u0442\u043e. \u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u0434\u043e\u0431\u0430\u0432\u043b\u0435\u043d\u0438\u044f \u043d\u0430\u0448\u0435\u0433\u043e \u0442\u0435\u0441\u0442\u0430 \u0432 \u043a\u043b\u0430\u0441\u0441 <code>PropertiesTest<\/code>:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Feature\\Api;      use Tests\\TestCase; use Illuminate\\Foundation\\Testing\\RefreshDatabase;      class PropertiesTest extends TestCase   { use RefreshDatabase;  \/** @test *\/   public function can_get_all_properties() {...}  \/** @test *\/   public function can_store_a_property() {...}  \/** @test *\/ public function can_update_a_property()  { $existingProperty = Property::factory()->create();   $newProperty = Property::factory()->make();      $response = $this->putJson(   route($this->routePrefix . 'update', $existingProperty),   $newProperty->toArray()  );   $response->assertJson([   'data' => [   \/\/ We keep the ID from the existing Property. 'id' => $existingProperty->id,   \/\/ But making sure the title changed. 'title' => $newProperty->title ] ]);      $this->assertDatabaseHas(   'properties',   $newProperty->toArray()   ); } <\/code><\/pre>\n<p>\u0417\u0430\u043f\u0443\u0441\u043a\u0430\u044f \u043d\u0430\u0448\u0438 \u0442\u0435\u0441\u0442\u044b, \u043c\u044b \u0437\u043d\u0430\u0435\u043c, \u0447\u0442\u043e \u043d\u0430\u0448\u0430 \u043f\u0435\u0440\u0432\u0430\u044f \u043e\u0448\u0438\u0431\u043a\u0430 \u0441\u0432\u044f\u0437\u0430\u043d\u0430 \u0441 \u043d\u0435\u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0449\u0438\u043c \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u043e\u043c: <code>api.properties.update<\/code>; \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0431\u044b\u0441\u0442\u0440\u043e \u0434\u043e\u0431\u0430\u0432\u0438\u043c \u0435\u0433\u043e \u0432 \u043d\u0430\u0448 \u0444\u0430\u0439\u043b <code>routes\/api.php<\/code>:<\/p>\n<pre><code class=\"php\">use App\\Http\\Controllers\\Api\\PropertyController;   Route::put(  'properties\/{property}',  [PropertyController::class, 'update'] )->name('api.properties.update');<\/code><\/pre>\n<p>\u041c\u044b \u0443\u0436\u0435 \u0437\u043d\u0430\u0435\u043c, \u0447\u0442\u043e \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0430\u044f \u043e\u0448\u0438\u0431\u043a\u0430 \u043d\u0430\u043f\u043e\u043c\u043d\u0438\u0442 \u043d\u0430\u043c \u043e \u0442\u043e\u043c, \u0447\u0442\u043e \u043c\u0435\u0442\u043e\u0434 <code>update<\/code> \u043d\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use App\\Models\\Property;   use Illuminate\\Http\\Request;   use Illuminate\\Http\\JsonResponse;   use App\\Http\\Controllers\\Controller;   use App\\Http\\Requests\\PropertyRequest;      class PropertyController extends Controller   {   public function index() : JsonResponse {...}    public function store(PropertyRequest $request): JsonResponse {...}  public function update(Request $request, Property $property)  { return response()->json([ 'data' => tap($property)->update($request->all()) ]); }<\/code><\/pre>\n<p>\u041c\u0435\u0442\u043e\u0434 <code>update<\/code> \u043f\u0440\u0438\u043d\u0438\u043c\u0430\u0435\u0442 Request (\u0437\u0430\u043f\u0440\u043e\u0441) \u0432 \u043a\u0430\u0447\u0435\u0441\u0442\u0432\u0435 \u043f\u0435\u0440\u0432\u043e\u0433\u043e \u043f\u0430\u0440\u0430\u043c\u0435\u0442\u0440\u0430 (\u043e\u0431\u0440\u0430\u0442\u0438\u0442\u0435 \u0432\u043d\u0438\u043c\u0430\u043d\u0438\u0435, \u044f \u043d\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043b PropertyRequest, \u0442\u0430\u043a \u043a\u0430\u043a \u043c\u044b \u043d\u0435 \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u043b\u0438 \u0442\u0435\u0441\u0442) \u0438 Property, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043c\u044b \u043e\u0431\u043d\u043e\u0432\u043b\u044f\u0435\u043c, \u043f\u0440\u0438\u0445\u043e\u0434\u044f\u0449\u0435\u0435 \u0438\u0437 \u044d\u043d\u0434\u043f\u043e\u0439\u043d\u0442 \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e <a href=\"https:\/\/laravel.com\/docs\/8.x\/routing#implicit-binding\">Route Implicit Binding<\/a> (\u043d\u0435\u044f\u0432\u043d\u0430\u044f \u043f\u0440\u0438\u0432\u044f\u0437\u043a\u0430 \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0430) \u043e\u0442 Laravel.<\/p>\n<p>\u041c\u044b \u0442\u0430\u043a\u0436\u0435 \u043c\u043e\u0436\u0435\u043c \u043e\u0442\u043c\u0435\u0442\u0438\u0442\u044c \u043c\u0435\u0442\u043e\u0434 <a href=\"https:\/\/laravel.com\/docs\/8.x\/collections#method-tap\">tap<\/a>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439, \u043f\u043e \u0441\u0443\u0442\u0438, \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 \u044d\u043b\u0435\u043c\u0435\u043d\u0442, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0432\u044b \u0435\u043c\u0443 \u043f\u0435\u0440\u0435\u0434\u0430\u0435\u0442\u0435, \u043f\u0440\u0438 \u044d\u0442\u043e\u043c \u0438\u043c\u0435\u044f \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442\u044c \u0441\u0432\u044f\u0437\u044b\u0432\u0430\u0442\u044c \u0441 \u043d\u0438\u043c \u043c\u0435\u0442\u043e\u0434\u044b; \u0432 \u043a\u043e\u043d\u0446\u0435 \u043e\u043d \u0432\u0435\u0440\u043d\u0435\u0442 \u043c\u043e\u0434\u0435\u043b\u044c \u043f\u043e\u0441\u043b\u0435 \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u044f, \u0432 \u043e\u0442\u043b\u0438\u0447\u0438\u0435 \u043e\u0442 \u0430\u043b\u044c\u0442\u0435\u0440\u043d\u0430\u0442\u0438\u0432\u043d\u043e\u0433\u043e \u0432\u0430\u0440\u0438\u0430\u043d\u0442\u0430:<\/p>\n<pre><code class=\"php\">public function update(Request $request, Property $property): JsonResponse { $property->update($request->all());  return response()->json([ 'data' => $property ]); }<\/code><\/pre>\n<p>\u0438 \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0442\u043e\u0436\u0435 \u044f\u0432\u043b\u044f\u0435\u0442\u0441\u044f \u0432\u0430\u043b\u0438\u0434\u043d\u044b\u043c, \u043e\u043d \u043f\u0440\u043e\u0441\u0442\u043e \u0442\u0440\u0435\u0431\u0443\u0435\u0442 \u0434\u043e\u043f\u043e\u043b\u043d\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0439 \u0441\u0442\u0440\u043e\u043a\u0438.<\/p>\n<p>\u041d\u0430 \u0434\u0430\u043d\u043d\u043e\u043c \u044d\u0442\u0430\u043f\u0435 \u043c\u044b \u0434\u043e\u043b\u0436\u043d\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u0442\u044c \u043f\u0440\u043e\u0445\u043e\u0436\u0434\u0435\u043d\u0438\u0435 \u0442\u0435\u0441\u0442\u0430. \u041d\u0430\u043c \u043f\u0440\u043e\u0441\u0442\u043e \u043d\u0435 \u0445\u0432\u0430\u0442\u0430\u0435\u0442 \u0442\u0435\u0441\u0442\u043e\u0432 \u0432\u0430\u043b\u0438\u0434\u0430\u0446\u0438\u0438, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e, \u0432\u0435\u0440\u043d\u0443\u0432\u0448\u0438\u0441\u044c \u043a \u043d\u0430\u0448\u0435\u043c\u0443 \u0444\u0430\u0439\u043b\u0443 <code>tests\\Unit\\Http\\Requests\\PropertyRequestTest.php<\/code> \u0438 \u0440\u0430\u0441\u0441\u043c\u043e\u0442\u0440\u0438\u043c, \u043a\u0430\u043a \u0432\u043a\u043b\u044e\u0447\u0438\u0442\u044c \u0432\u044b\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u0435 <code>update<\/code> \u0432 \u043d\u0430\u0448\u0438 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0449\u0438\u0435 \u0442\u0435\u0441\u0442\u044b:<\/p>\n<pre><code class=\"php\">use RefreshDatabase;   private string $routePrefix = 'api.properties.';   \/**   * @test   * @throws \\Throwable  *\/  public function type_is_required()  {  $validatedField = 'type';  $brokenRule = null;  $property = Property::factory()->make([  $validatedField => $brokenRule  ]);   $this->postJson(  route($this->routePrefix . 'store'),  $property->toArray()  )->assertJsonValidationErrors($validatedField);   \/\/ Update assertion $existingProperty = Property::factory()->create();  $newProperty = Property::factory()->make([  $validatedField => $brokenRule  ]);   $this->putJson( route($this->routePrefix . 'update', $existingProperty),   $newProperty->toArray()   )->assertJsonValidationErrors($validatedField); }<\/code><\/pre>\n<p>\u0412 \u0431\u043b\u043e\u043a\u0435 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u044f Update \u043c\u044b:<\/p>\n<ul>\n<li>\n<p>\u0421\u043e\u0437\u0434\u0430\u043b\u0438 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0449\u0435\u0435 Property (\u0441\u0432\u043e\u0439\u0441\u0442\u0432\u043e), \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043c\u044b \u0445\u043e\u0442\u0438\u043c \u043e\u0431\u043d\u043e\u0432\u0438\u0442\u044c.<\/p>\n<\/li>\n<li>\n<p>\u0421\u043e\u0437\u0434\u0430\u043b\u0438 \u043d\u0435\u043f\u0435\u0440\u0441\u0438\u0441\u0442\u0435\u043d\u0442\u043d\u043e\u0435 \u0444\u0430\u0431\u0440\u0438\u0447\u043d\u043e\u0435 Property \u0441 \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0435\u043c\u044b\u043c \u043f\u043e\u043b\u0435\u043c \u0438 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435\u043c, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043d\u0430\u0440\u0443\u0448\u0438\u0442 \u0442\u0435\u0441\u0442 (\u0432 \u0434\u0430\u043d\u043d\u043e\u043c \u0441\u043b\u0443\u0447\u0430\u0435 null).<\/p>\n<\/li>\n<li>\n<p>\u0417\u0430\u0442\u0435\u043c \u043c\u044b \u0441\u0434\u0435\u043b\u0430\u043b\u0438 <code>PUT<\/code>-\u0437\u0430\u043f\u0440\u043e\u0441 \u043a \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0443 <code>api.properties.update<\/code>, \u043f\u0435\u0440\u0435\u0434\u0430\u0432 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0449\u0435\u0435 Property \u0432 \u043a\u0430\u0447\u0435\u0441\u0442\u0432\u0435 \u043f\u0430\u0440\u0430\u043c\u0435\u0442\u0440\u0430, \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u0438\u043c\u0435\u043d\u043d\u043e \u044d\u0442\u043e\u0433\u043e \u043e\u0436\u0438\u0434\u0430\u0435\u0442 \u043d\u0430\u0448 \u043c\u0430\u0440\u0448\u0440\u0443\u0442.<\/p>\n<\/li>\n<li>\n<p>\u0418 \u043c\u044b \u0441\u0434\u0435\u043b\u0430\u043b\u0438 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u0435 \u0434\u043b\u044f \u044d\u0442\u043e\u0433\u043e \u0437\u0430\u043f\u0440\u043e\u0441\u0430, \u043f\u043e\u0434\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u044e\u0449\u0435\u0435, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u043b\u0438 JSON-\u043e\u0448\u0438\u0431\u043a\u0443 .<\/p>\n<\/li>\n<\/ul>\n<p>\u0415\u0434\u0438\u043d\u0441\u0442\u0432\u0435\u043d\u043d\u043e\u0435, \u0447\u0435\u0433\u043e \u043d\u0435 \u0445\u0432\u0430\u0442\u0430\u0435\u0442, \u044d\u0442\u043e \u043f\u043e\u0432\u0442\u043e\u0440\u0438\u0442\u044c \u0442\u0435\u0441\u0442\u044b \u0434\u043b\u044f \u043e\u0441\u0442\u0430\u043b\u044c\u043d\u044b\u0445 \u043f\u043e\u043b\u0435\u0439, \u0437\u0430\u043c\u0435\u043d\u0438\u0432 <code>$validatedField<\/code> \u0438 <code>$brokenRule<\/code> \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0435\u043d\u043d\u043e, \u0438 \u0432\u043d\u0435\u0434\u0440\u0438\u0442\u044c <code>PropertyRequest<\/code> \u0432 \u043d\u0430\u0448 \u043d\u043e\u0432\u044b\u0439 \u043c\u0435\u0442\u043e\u0434 <code>update<\/code> \u0432\u043c\u0435\u0441\u0442\u043e \u043a\u043b\u0430\u0441\u0441\u0430 Laravel&#8217;s Request \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c:<\/p>\n<pre><code>public function update(PropertyRequest $request, Property $property) <\/code><\/pre>\n<p>\u0418 \u0443 \u043d\u0430\u0441 \u0435\u0441\u0442\u044c \u043f\u0440\u043e\u0439\u0434\u0435\u043d\u043d\u044b\u0439 \u0442\u0435\u0441\u0442.<\/p>\n<p>\u041e\u0442\u043b\u0438\u0447\u043d\u043e, \u043f\u0435\u0440\u0435\u0445\u043e\u0434\u0438\u043c \u043a \u0444\u0438\u043d\u0430\u043b\u044c\u043d\u043e\u043c\u0443 \u0442\u0435\u0441\u0442\u0443.<\/p>\n<h3>\u0422\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043c\u0435\u0442\u043e\u0434\u0430 Destroy<\/h3>\n<p>\u042d\u0442\u043e \u0431\u0443\u0434\u0435\u0442 \u0441\u0430\u043c\u044b\u0439 \u043a\u043e\u0440\u043e\u0442\u043a\u0438\u0439 \u0442\u0435\u0441\u0442, \u0441\u0434\u0435\u043b\u0430\u043d\u043d\u044b\u0439 \u0432 \u044d\u0442\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0435, \u0442\u0430\u043a \u043a\u0430\u043a \u043c\u044b \u043f\u0440\u043e\u0441\u0442\u043e \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u043c, \u0447\u0442\u043e \u043f\u0440\u0438 \u0434\u043e\u0441\u0442\u0438\u0436\u0435\u043d\u0438\u0438 \u044d\u043d\u0434\u043f\u043e\u0439\u043d\u0442 <code>delete<\/code> \u0443\u0434\u0430\u043b\u0438\u043c \u043c\u043e\u0434\u0435\u043b\u044c Property, \u0430 \u0442\u0430\u043a\u0436\u0435 \u0432\u0435\u0440\u043d\u0435\u043c \u043e\u0442\u0432\u0435\u0442 \u0441\u043e \u0441\u0442\u0430\u0442\u0443\u0441-\u043a\u043e\u0434\u043e\u043c <code>204: No Content<\/code> (\u043d\u0435\u0442 \u043a\u043e\u043d\u0442\u0435\u043d\u0442\u0430).<\/p>\n<pre><code class=\"php\">\/** @test *\/ public function can_update_a_property() {...}  \/** @test *\/ public function can_delete_a_property()  { $existingProperty = Property::factory()->create();  $this->deleteJson( route($this->routePrefix . 'destroy', $existingProperty) )->assertNoContent();  \/\/ You can also use assertStatus(204) instead of assertNoContent()      \/\/ in case you're using a Laravel version that does not have this assertion.          \/\/ (I believe it is available from v7.x onwards)  \/\/ Finally we just assert the `properties` table does not contain the model that we just deleted. $this->assertDatabaseMissing(   'properties',   $existingProperty->toArray()   ); }<\/code><\/pre>\n<p>\u0415\u0441\u043b\u0438 \u043c\u044b \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0435\u0433\u043e, \u0442\u043e \u043f\u043e\u043b\u0443\u0447\u0438\u043c \u043e\u0436\u0438\u0434\u0430\u0435\u043c\u0443\u044e \u043e\u0448\u0438\u0431\u043a\u0443, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u0442\u043e\u043c, \u0447\u0442\u043e \u0443 \u043d\u0430\u0441 \u043d\u0435\u0442 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u0433\u043e \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0430, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0434\u043e\u0431\u0430\u0432\u0438\u043c \u0435\u0433\u043e:<\/p>\n<pre><code class=\"php\">Route::delete(  'properties',  [PropertyController::class, 'destroy']  )->name('api.properties.destroy');<\/code><\/pre>\n<p>\u0418 \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u0435 \u0435\u0433\u043e \u0441\u043d\u043e\u0432\u0430, \u0447\u0442\u043e\u0431\u044b \u043e\u0431\u043d\u0430\u0440\u0443\u0436\u0438\u0442\u044c, \u0447\u0442\u043e \u043c\u0435\u0442\u043e\u0434 <code>destroy<\/code> \u043d\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442; \u044f \u0434\u043e\u0431\u0430\u0432\u043b\u044e \u0435\u0433\u043e \u0432 \u043d\u0430\u0448 <code>PropertyController<\/code> \u043d\u0438\u0436\u0435 \u043c\u0435\u0442\u043e\u0434\u0430 <code>update<\/code>:<\/p>\n<pre><code class=\"php\">public function update(PropertyRequest $request, Property $property) {...}  public function destroy(Property $property) { $property->delete();  return response([], 204); }<\/code><\/pre>\n<p>\u0414\u0435\u0440\u0436\u0443 \u043f\u0430\u0440\u0438, \u044d\u0442\u043e \u043f\u0440\u043e\u0439\u0434\u0435\u0442, \u0432\u0435\u0440\u043d\u043e?<\/p>\n<p>\u041c\u0435\u0442\u043e\u0434 <code>destroy<\/code> \u0434\u043e\u0432\u043e\u043b\u044c\u043d\u043e \u043f\u0440\u043e\u0441\u0442; \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u043e\u0436\u0438\u0434\u0430\u0435\u043c\u043e\u0435 \u0441\u0432\u043e\u0439\u0441\u0442\u0432\u043e \u0438\u0437 Route (\u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0430) \u0438, \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043d\u0435\u044f\u0432\u043d\u0430\u044f \u043f\u0440\u0438\u0432\u044f\u0437\u043a\u0430 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u043b\u0430, \u043a\u0430\u043a\u0443\u044e \u043c\u043e\u0434\u0435\u043b\u044c Property \u043c\u044b \u0445\u043e\u0442\u0438\u043c \u0443\u0434\u0430\u043b\u0438\u0442\u044c, \u043c\u044b \u043f\u0440\u043e\u0441\u0442\u043e \u0437\u0430\u043f\u0443\u0441\u043a\u0430\u0435\u043c \u043c\u0435\u0442\u043e\u0434 <code>delete()<\/code> \u043d\u0430 \u043d\u0435\u043c, \u0430 \u0437\u0430\u0442\u0435\u043c \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c \u043e\u0442\u0432\u0435\u0442.<\/p>\n<ul>\n<li>\n<p>\u041f\u0440\u0438\u043c\u0435\u0447\u0430\u043d\u0438\u0435: \u044f \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0438\u0437\u0438\u0440\u043e\u0432\u0430\u043b \u043e\u0442\u0432\u0435\u0442\u044b \u0434\u043b\u044f \u044d\u0442\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0438, \u043d\u043e \u0432\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0442\u044c \u0442\u043e, \u0447\u0442\u043e \u0432\u0430\u043c \u043d\u0443\u0436\u043d\u043e.<\/p>\n<\/li>\n<\/ul>\n<h3>\u0417\u0430\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0435<\/h3>\n<p>\u0425\u043e\u0442\u044f \u044f \u043f\u043e\u0441\u0442\u0430\u0440\u0430\u043b\u0441\u044f \u0441\u0434\u0435\u043b\u0430\u0442\u044c \u044d\u0442\u043e\u0442 \u043f\u0440\u0438\u043c\u0435\u0440 \u043c\u0430\u043a\u0441\u0438\u043c\u0430\u043b\u044c\u043d\u043e \u043f\u0440\u0438\u0431\u043b\u0438\u0436\u0435\u043d\u043d\u044b\u043c \u043a \u0440\u0435\u0430\u043b\u044c\u043d\u043e\u0441\u0442\u0438, \u0435\u0441\u0442\u044c \u043a\u043e\u0435-\u0447\u0442\u043e, \u0447\u0442\u043e \u0441\u043b\u0435\u0434\u043e\u0432\u0430\u043b\u043e \u0431\u044b \u0441\u0434\u0435\u043b\u0430\u0442\u044c \u043f\u043e-\u0434\u0440\u0443\u0433\u043e\u043c\u0443, \u0431\u0443\u0434\u044c \u044d\u0442\u043e \u0440\u0435\u0430\u043b\u044c\u043d\u043e\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0435:<\/p>\n<p>\u0412\u043c\u0435\u0441\u0442\u043e \u0432\u043e\u0437\u0432\u0440\u0430\u0442\u0430 JSON-\u043e\u0442\u0432\u0435\u0442\u043e\u0432, \u043a\u0430\u043a \u043c\u044b \u0434\u0435\u043b\u0430\u043b\u0438, \u044f \u0431\u044b \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043b <a href=\"https:\/\/laravel.com\/docs\/8.x\/eloquent-resources#introduction\">API Resources<\/a> (\u0440\u0435\u0441\u0443\u0440\u0441\u044b API). \u041f\u0440\u0438\u0447\u0438\u043d\u0430 \u0432 \u0442\u043e\u043c, \u0447\u0442\u043e \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e, \u043c\u043d\u0435 \u0437\u0430\u0445\u043e\u0447\u0435\u0442\u0441\u044f \u0432\u043d\u0435\u0441\u0442\u0438 \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u043e \u0438\u0437\u043c\u0435\u043d\u0435\u043d\u0438\u0439 \u0432 \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u044e\/\u043c\u043e\u0434\u0435\u043b\u044c, \u043a\u043e\u0442\u043e\u0440\u0443\u044e \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e \u0432\u0435\u0440\u043d\u0443\u0442\u044c, \u0430 \u0440\u0435\u0441\u0443\u0440\u0441 API \u043f\u043e\u0437\u0432\u043e\u043b\u0438\u0442 \u044d\u0442\u043e \u0441\u0434\u0435\u043b\u0430\u0442\u044c. \u0414\u043e\u043f\u043e\u043b\u043d\u0438\u0442\u0435\u043b\u044c\u043d\u044b\u0435 \u043f\u0440\u0438\u043c\u0435\u0440\u044b \u043c\u043e\u0436\u043d\u043e \u043d\u0430\u0439\u0442\u0438 \u0432 \u0434\u043e\u043a\u0443\u043c\u0435\u043d\u0442\u0430\u0446\u0438\u0438.<\/p>\n<p>\u041f\u043e\u0447\u0442\u0438 \u043a\u0430\u0436\u0434\u0430\u044f \u0441\u043a\u0432\u043e\u0437\u043d\u0430\u044f \u0444\u0438\u0447\u0430, \u043a\u043e\u0442\u043e\u0440\u0443\u044e \u0432\u0430\u043c \u043d\u0443\u0436\u043d\u043e \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c, \u0438\u043c\u0435\u0435\u0442 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443, \u0441\u0445\u043e\u0436\u0443\u044e \u0441 \u0432\u044b\u0448\u0435\u0443\u043f\u043e\u043c\u044f\u043d\u0443\u0442\u044b\u043c\u0438 \u0442\u0435\u0441\u0442\u0430\u043c\u0438, \u043f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u043c\u044b \u0434\u0435\u043b\u0430\u0435\u043c \u0437\u0430\u043f\u0440\u043e\u0441\u044b \u043a \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u044e \u0438 \u043e\u0436\u0438\u0434\u0430\u0435\u043c \u043e\u0442 \u043d\u0435\u0433\u043e \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0430, \u0438\u0437 \u043a\u043e\u0442\u043e\u0440\u043e\u0433\u043e \u0432\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u043b\u0435\u0433\u043a\u043e \u043f\u043e\u0434\u0441\u0442\u0440\u043e\u0438\u0442\u044c \u0442\u0435\u0441\u0442 \u043f\u043e\u0434 \u0441\u0432\u043e\u0438 \u043d\u0443\u0436\u0434\u044b.<\/p>\n<p>\u041d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0438\u0437 \u043f\u0440\u0438\u0447\u0438\u043d, \u043f\u043e \u043a\u043e\u0442\u043e\u0440\u044b\u043c \u043a\u043e\u043c\u0430\u043d\u0434\u0430 \u043d\u0435 \u0432\u043d\u0435\u0434\u0440\u044f\u0435\u0442 \u0442\u0435\u0441\u0442\u044b, \u043f\u043e \u043c\u043e\u0435\u043c\u0443 \u043e\u043f\u044b\u0442\u0443, \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u0443\u0431\u0435\u0436\u0434\u0435\u043d\u0438\u0438, \u0447\u0442\u043e \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043e\u0442\u043d\u0438\u043c\u0435\u0442 \u0432\u0440\u0435\u043c\u044f. \u041a\u0430\u043a \u043c\u044b \u0432\u0438\u0434\u0438\u043c, \u0432\u044b \u043c\u043e\u0436\u0435\u0442\u0435 \u043a\u043e\u043f\u0438\u043f\u0430\u0441\u0442\u0438\u0442\u044c \u0431\u043e\u043b\u044c\u0448\u0438\u043d\u0441\u0442\u0432\u043e \u0442\u0435\u0441\u0442\u043e\u0432 \u0438 \u0430\u0434\u0430\u043f\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0438\u0445 \u043a \u043d\u043e\u0432\u043e\u043c\u0443 \u0441\u0446\u0435\u043d\u0430\u0440\u0438\u044e \u043e\u0447\u0435\u043d\u044c \u0431\u044b\u0441\u0442\u0440\u043e, \u0430 \u0435\u0441\u043b\u0438 \u0432\u044b \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0438\u0437\u0438\u0440\u0443\u0435\u0442\u0435 \u0441\u0432\u043e\u0439 \u0440\u0430\u0431\u043e\u0447\u0438\u0439 \u043f\u0440\u043e\u0446\u0435\u0441\u0441 \u0438 \u043a\u043e\u0434, \u044d\u0442\u043e \u0431\u0443\u0434\u0435\u0442 \u0435\u0449\u0435 \u0431\u044b\u0441\u0442\u0440\u0435\u0435. \u041a\u043e\u043d\u0435\u0447\u043d\u043e, \u043a\u043e\u043f\u0438\u043f\u0430\u0441\u0442 \u0431\u0443\u0434\u0435\u0442 \u0432\u043e\u0437\u043c\u043e\u0436\u0435\u043d \u043d\u0435 \u0432 \u043a\u0430\u0436\u0434\u043e\u0439 \u0444\u0438\u0447\u0435, \u043d\u043e \u043a\u0430\u043a \u0442\u043e\u043b\u044c\u043a\u043e \u0432\u044b \u043d\u0430\u0447\u043d\u0435\u0442\u0435 \u0441\u0435\u0440\u044c\u0435\u0437\u043d\u043e \u043e\u0442\u043d\u043e\u0441\u0438\u0442\u044c\u0441\u044f \u043a \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044e, \u0432 \u0432\u0430\u0448\u0435\u0439 \u0433\u043e\u043b\u043e\u0432\u0435 \u0432\u0441\u0435 \u0432\u0441\u0442\u0430\u043d\u0435\u0442 \u043d\u0430 \u0441\u0432\u043e\u0438 \u043c\u0435\u0441\u0442\u0430, \u0438 \u0432\u044b \u043e\u0431\u043d\u0430\u0440\u0443\u0436\u0438\u0442\u0435 \u0437\u0430\u043a\u043e\u043d\u043e\u043c\u0435\u0440\u043d\u043e\u0441\u0442\u044c \u0432 \u0435\u0433\u043e \u043f\u0440\u043e\u0432\u0435\u0434\u0435\u043d\u0438\u0438.<\/p>\n<p>\u042f \u043f\u0440\u0435\u0434\u043b\u0430\u0433\u0430\u044e \u043d\u0430\u0447\u0430\u0442\u044c \u0441 \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f \u043d\u0435\u0431\u043e\u043b\u044c\u0448\u0438\u0445 \u0444\u0438\u0447 \u0438 \u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u044c \u043f\u043e\u0434\u0445\u043e\u0434\u0443 TDD \u043a\u0430\u043a \u043c\u043e\u0436\u043d\u043e \u0447\u0430\u0449\u0435. \u0412\u043e\u0437\u043c\u043e\u0436\u043d\u043e, \u0432\u0441\u043a\u043e\u0440\u0435 \u0432\u044b \u0440\u0435\u0448\u0438\u0442\u0435, \u0447\u0442\u043e \u0432\u0430\u043c \u043d\u0440\u0430\u0432\u0438\u0442\u0441\u044f \u0441\u043d\u0430\u0447\u0430\u043b\u0430 \u043a\u043e\u0434\u0438\u0442\u044c, \u0430 \u043f\u043e\u0442\u043e\u043c \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c; \u043d\u0430 \u0441\u0430\u043c\u043e\u043c \u0434\u0435\u043b\u0435 \u044d\u0442\u043e \u043d\u0435 \u0438\u043c\u0435\u0435\u0442 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f, \u043f\u043e\u043a\u0430 \u0432\u044b \u0442\u0435\u0441\u0442\u0438\u0440\u0443\u0435\u0442\u0435 \u0441\u0432\u043e\u0438 \u0444\u0438\u0447\u0438.<\/p>\n<p>\u041c\u044b \u0442\u043e\u043b\u044c\u043a\u043e \u043d\u0430\u0447\u0438\u043d\u0430\u0435\u043c \u0438\u0437\u0443\u0447\u0430\u0442\u044c TDD, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043e\u0436\u0438\u0434\u0430\u0439\u0442\u0435 \u043d\u043e\u0432\u044b\u0445 \u0441\u0442\u0430\u0442\u0435\u0439, \u043f\u043e\u0434\u043e\u0431\u043d\u044b\u0445 \u044d\u0442\u043e\u0439, \u0432 \u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u0431\u0443\u0434\u0443\u0442 \u0440\u0430\u0441\u043a\u0440\u044b\u0442\u044b \u043d\u043e\u0432\u044b\u0435 \u0442\u0435\u043c\u044b.<\/p>\n<hr\/>\n<p>&#171;Laravel 9&#187; \u0432\u044b\u0448\u043b\u0430 \u0432 \u0444\u0435\u0432\u0440\u0430\u043b\u0435 \u044d\u0442\u043e\u0433\u043e \u0433\u043e\u0434\u0430. \u0420\u0435\u043b\u0438\u0437 \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442 \u0434\u043e\u0441\u0442\u0430\u0442\u043e\u0447\u043d\u043e \u043c\u043d\u043e\u0433\u043e \u043d\u043e\u0432\u043e\u0432\u0432\u0435\u0434\u0435\u043d\u0438\u0439, \u0441\u0440\u0435\u0434\u0438 \u043a\u043e\u0442\u043e\u0440\u044b\u0445: \u043f\u043e\u0434\u0434\u0435\u0440\u0436\u043a\u0430 \u043a\u043e\u043c\u043f\u043e\u043d\u0435\u043d\u0442\u043e\u0432 Symfony 6, Symfony Mailer, Flysystem 3, \u0443\u043b\u0443\u0447\u0448\u0435\u043d\u043d\u044b\u0439 \u0432\u044b\u0432\u043e\u0434 route:list, \u0434\u0440\u0430\u0439\u0432\u0435\u0440\u0430 Laravel Scout, \u043d\u043e\u0432\u044b\u0439 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0441 \u0430\u043a\u0441\u0435\u0441\u0441\u043e\u0440\/\u043c\u0443\u0442\u0430\u0442\u043e\u0440 Eloquent \u0438 \u0440\u0430\u0437\u043b\u0438\u0447\u043d\u044b\u0435 \u0434\u0440\u0443\u0433\u0438\u0435 \u0438\u0441\u043f\u0440\u0430\u0432\u043b\u0435\u043d\u0438\u044f \u043e\u0448\u0438\u0431\u043e\u043a \u0438 \u0443\u043b\u0443\u0447\u0448\u0435\u043d\u0438\u044f \u0434\u043b\u044f \u0443\u0434\u043e\u0431\u0441\u0442\u0432\u0430 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f \u0444\u0440\u0435\u0439\u043c\u0432\u043e\u0440\u043a\u0430. \u041f\u0440\u0438\u0433\u043b\u0430\u0448\u0430\u0435\u043c \u043d\u0430 \u043e\u0442\u043a\u0440\u044b\u0442\u043e\u0435 \u0437\u0430\u043d\u044f\u0442\u0438\u0435, \u043d\u0430 \u043a\u043e\u0442\u043e\u0440\u043e\u043c \u043f\u043e\u0441\u0442\u0430\u0440\u0430\u0435\u043c\u0441\u044f \u0437\u0430\u0442\u0440\u043e\u043d\u0443\u0442\u044c \u0441\u0430\u043c\u044b\u0435 \u0432\u0430\u0436\u043d\u044b\u0435 \u0438\u0437 \u043d\u0438\u0445. \u0420\u0435\u0433\u0438\u0441\u0442\u0440\u0430\u0446\u0438\u044f \u0434\u043b\u044f \u0432\u0441\u0435\u0445 \u0436\u0435\u043b\u0430\u044e\u0449\u0438\u0445 <a href=\"https:\/\/otus.pw\/CTKE\/\"><strong>\u043f\u043e \u0441\u0441\u044b\u043b\u043a\u0435.<\/strong><\/a><\/p>\n<\/p>\n<\/div>\n<\/div>\n<\/div>\n<div class=\"v-portal\" style=\"display:none;\"><\/div>\n<\/div>\n<p> <!----> <!----><br \/> \u0441\u0441\u044b\u043b\u043a\u0430 \u043d\u0430 \u043e\u0440\u0438\u0433\u0438\u043d\u0430\u043b \u0441\u0442\u0430\u0442\u044c\u0438 <a href=\"https:\/\/habr.com\/ru\/company\/otus\/blog\/674310\/\"> https:\/\/habr.com\/ru\/company\/otus\/blog\/674310\/<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<div><\/div>\n<div id=\"post-content-body\">\n<div>\n<div class=\"article-formatted-body article-formatted-body article-formatted-body_version-2\">\n<div xmlns=\"http:\/\/www.w3.org\/1999\/xhtml\">\n<figure class=\"full-width\"><figcaption><\/figcaption><\/figure>\n<p>\u041f\u0440\u0438\u0432\u0435\u0442, <em>Artisans (\u0430\u043d\u0433\u043b. \u041c\u0430\u0441\u0442\u0435\u0440\u0430; \u043f\u0440\u043e\u0433\u0440. Artisan \u2014 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043a\u043e\u043c\u0430\u043d\u0434\u043d\u043e\u0439 \u0441\u0442\u0440\u043e\u043a\u0438, \u0432\u0445\u043e\u0434\u044f\u0449\u0438\u0439 \u0432 \u0441\u043e\u0441\u0442\u0430\u0432 Laravel)<\/em>, \u043c\u0435\u043d\u044f \u0437\u043e\u0432\u0443\u0442 <a href=\"https:\/\/alberto-rosas.dev\/\">\u0410\u043b\u044c\u0431\u0435\u0440\u0442\u043e \u0420\u043e\u0441\u0430\u0441<\/a> (Alberto Rosas), \u044f \u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0441\u044c Laravel \u0443\u0436\u0435 \u043c\u043d\u043e\u0433\u043e \u043b\u0435\u0442, \u0438 \u043e\u0434\u043d\u0430 \u0438\u0437 \u0441\u0430\u043c\u044b\u0445 \u043f\u043e\u043b\u0435\u0437\u043d\u044b\u0445 \u0438 \u0441\u0442\u043e\u044f\u0449\u0438\u0445 \u0432\u0435\u0449\u0435\u0439, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u044f \u0443\u0437\u043d\u0430\u043b, \u2014 \u044d\u0442\u043e \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u044b\u0445 \u0442\u0435\u0441\u0442\u043e\u0432\u044b\u0445 \u0441\u044c\u044e\u0442\u043e\u0432 \u0434\u043b\u044f \u0441\u0432\u043e\u0438\u0445 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439. \u041e\u0447\u0435\u043d\u044c \u043f\u0440\u0438\u044f\u0442\u043d\u043e \u0432\u0438\u0434\u0435\u0442\u044c, \u0447\u0442\u043e \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u0432\u0441\u0435 \u0447\u0430\u0449\u0435 \u043f\u0440\u0430\u043a\u0442\u0438\u043a\u0443\u0435\u0442\u0441\u044f \u0432 \u0441\u043e\u043e\u0431\u0449\u0435\u0441\u0442\u0432\u0435 Laravel, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0432 \u044d\u0442\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0435 \u043c\u044b \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u043e\u0441\u043d\u043e\u0432 TDD (Test Driven Development. \u0420\u0430\u0437\u0440\u0430\u0431\u043e\u0442\u043a\u0430 \u0447\u0435\u0440\u0435\u0437 \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435) \u0432 Laravel \u0438 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0442\u0435\u043c\u0443 \u0432 \u0434\u0440\u0443\u0433\u0438\u0445 \u0441\u0442\u0430\u0442\u044c\u044f\u0445.<\/p>\n<p>\u0412\u043e\u0442 \u0447\u0442\u043e \u043d\u0430\u043c \u043f\u0440\u0435\u0434\u0441\u0442\u043e\u0438\u0442 \u043e\u0441\u0432\u043e\u0438\u0442\u044c:<\/p>\n<ul>\n<li>\n<p>\u0421\u043e\u0437\u0434\u0430\u043d\u0438\u0435 API \u0441 \u043d\u0443\u043b\u044f \u0441 \u0443\u043f\u043e\u0440\u043e\u043c \u043d\u0430 \u0431\u0430\u0437\u043e\u0432\u044b\u0435 \u0444\u0438\u0447\u0438 <a href=\"https:\/\/www.codecademy.com\/articles\/what-is-crud\">CRUD<\/a>.<\/p>\n<\/li>\n<li>\n<p>\u0412\u043d\u0435\u0434\u0440\u0438\u043c <a href=\"https:\/\/medium.com\/@sameernyaupane\/php-test-driven-development-part-1-introduction-5483362d79b5\">TDD<\/a> \u0441 \u0441\u0430\u043c\u043e\u0433\u043e \u043d\u0430\u0447\u0430\u043b\u0430, \u0447\u0442\u043e\u0431\u044b \u043f\u0440\u043e\u0438\u043b\u043b\u044e\u0441\u0442\u0440\u0438\u0440\u043e\u0432\u0430\u0442\u044c, \u043a\u0430\u043a \u0441\u043e\u0437\u0434\u0430\u0432\u0430\u0442\u044c \u0442\u0435\u0441\u0442\u0438\u0440\u0443\u0435\u043c\u044b\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f Laravel.<\/p>\n<\/li>\n<\/ul>\n<h3>\u0412\u0432\u0435\u0434\u0435\u043d\u0438\u0435<\/h3>\n<p>\u0417\u0430\u0434\u0430\u0447\u0430 \u0434\u0430\u043d\u043d\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0438 \u2014 \u043f\u043e\u043a\u0430\u0437\u0430\u0442\u044c, \u0447\u0442\u043e TDD \u043d\u0435 \u043e\u0431\u044f\u0437\u0430\u0442\u0435\u043b\u044c\u043d\u043e \u0434\u043e\u043b\u0436\u0435\u043d \u0431\u044b\u0442\u044c \u0442\u0440\u0443\u0434\u043d\u044b\u043c \u0438\u043b\u0438 \u043c\u0443\u0447\u0438\u0442\u0435\u043b\u044c\u043d\u044b\u043c, \u0447\u0442\u043e\u0431\u044b \u0441\u0434\u0435\u043b\u0430\u0442\u044c \u0435\u0433\u043e \u0447\u0430\u0441\u0442\u044c\u044e \u0440\u0430\u0431\u043e\u0447\u0435\u0433\u043e \u043f\u0440\u043e\u0446\u0435\u0441\u0441\u0430 \u0434\u043b\u044f \u0432\u0430\u0441 \u0438\u043b\u0438 \u0432\u0430\u0448\u0435\u0439 \u043a\u043e\u043c\u0430\u043d\u0434\u044b. \u0412\u0430\u043c \u043f\u0440\u043e\u0441\u0442\u043e \u043d\u0443\u0436\u043d\u043e \u043f\u043e\u043d\u044f\u0442\u044c, \u0441 \u0447\u0435\u0433\u043e \u043d\u0430\u0447\u0430\u0442\u044c \u0438 \u0447\u0442\u043e \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c.<\/p>\n<p>\u041c\u043d\u0435 \u043d\u0435 \u043f\u043e\u0442\u0440\u0435\u0431\u043e\u0432\u0430\u043b\u043e\u0441\u044c \u043c\u043d\u043e\u0433\u043e \u0432\u0440\u0435\u043c\u0435\u043d\u0438, \u0447\u0442\u043e\u0431\u044b \u043f\u0440\u0435\u0432\u0440\u0430\u0442\u0438\u0442\u044c TDD \u0432 \u043f\u0440\u0438\u0432\u044b\u0447\u043a\u0443 \u0438 \u043d\u0430\u0439\u0442\u0438 \u043f\u043e\u0434\u0445\u043e\u0434\u044f\u0449\u0438\u0439 \u0434\u043b\u044f \u043c\u0435\u043d\u044f \u0440\u0430\u0431\u043e\u0447\u0438\u0439 \u043f\u0440\u043e\u0446\u0435\u0441\u0441. \u0412\u0430\u0436\u043d\u043e \u0438\u043c\u0435\u0442\u044c \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043d\u044b\u0439 \u0440\u0430\u0431\u043e\u0447\u0438\u0439 \u043f\u0440\u043e\u0446\u0435\u0441\u0441; \u0437\u043d\u0430\u043d\u0438\u0435 \u0442\u043e\u0433\u043e, \u0447\u0442\u043e \u0432\u044b \u0431\u0443\u0434\u0435\u0442\u0435 \u0434\u0435\u043b\u0430\u0442\u044c \u0432 \u043f\u0435\u0440\u0432\u0443\u044e \u043e\u0447\u0435\u0440\u0435\u0434\u044c \u0432 \u0442\u0438\u043f\u0438\u0447\u043d\u043e\u043c \u043f\u0440\u043e\u0435\u043a\u0442\u0435, \u043c\u043e\u0436\u0435\u0442 \u043f\u043e\u043c\u043e\u0447\u044c \u0432\u0430\u043c \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u0441\u0432\u043e\u044e \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u0443\u044e \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443, \u043e\u0440\u0433\u0430\u043d\u0438\u0437\u043e\u0432\u0430\u0442\u044c \u0432\u0441\u0435 \u0442\u0430\u043a\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c, \u0447\u0442\u043e\u0431\u044b \u0432\u044b \u0437\u043d\u0430\u043b\u0438, \u0433\u0434\u0435 \u0447\u0442\u043e \u043d\u0430\u0445\u043e\u0434\u0438\u0442\u0441\u044f \u0432 \u0432\u0430\u0448\u0435\u043c \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0438, \u0438 \u043d\u0435\u043c\u043d\u043e\u0433\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0438\u0437\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0432\u0430\u0448\u0438 \u043b\u0438\u0447\u043d\u044b\u0435\/\u043a\u043b\u0438\u0435\u043d\u0442\u0441\u043a\u0438\u0435 \u043f\u0440\u043e\u0435\u043a\u0442\u044b.<\/p>\n<p>\u0414\u0440\u0443\u0433\u0438\u043c\u0438 \u0441\u043b\u043e\u0432\u0430\u043c\u0438, TDD \u043f\u043e\u043c\u043e\u0433\u0430\u0435\u0442 \u0432\u0430\u043c \u043a\u043e\u0434\u0438\u0442\u044c \u0431\u044b\u0441\u0442\u0440\u0435\u0435 \u0438 \u0443\u0432\u0435\u0440\u0435\u043d\u043d\u0435\u0435. \u042f \u0443\u043f\u043e\u043c\u0438\u043d\u0430\u043b \u0440\u0430\u043d\u0435\u0435 \u043e \u043f\u043e\u043d\u0438\u043c\u0430\u043d\u0438\u0438 \u0442\u043e\u0433\u043e, \u0447\u0442\u043e \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0432 \u043f\u0435\u0440\u0432\u0443\u044e \u043e\u0447\u0435\u0440\u0435\u0434\u044c. \u041d\u043e \u043d\u0430 \u0441\u0430\u043c\u043e\u043c \u0434\u0435\u043b\u0435 \u044d\u0442\u043e \u043d\u0435 \u0438\u043c\u0435\u0435\u0442 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f, \u043c\u044b \u0441\u0430\u043c\u0438 \u043d\u0430\u043f\u0440\u0430\u0432\u0438\u043c \u0432\u0430\u0441 \u043a \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c \u0442\u0435\u0441\u0442\u0430\u043c, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0435\u0434\u0438\u043d\u0441\u0442\u0432\u0435\u043d\u043d\u043e\u0435, \u0447\u0442\u043e \u0432\u0430\u043c \u043d\u0443\u0436\u043d\u043e \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u0437\u043d\u0430\u0442\u044c, \u044d\u0442\u043e \u0444\u0438\u0447\u0430, \u043a\u043e\u0442\u043e\u0440\u0443\u044e \u0432\u044b \u0445\u043e\u0442\u0438\u0442\u0435 \u043f\u0440\u043e\u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c.<\/p>\n<h3>\u0422\u0440\u0435\u0431\u043e\u0432\u0430\u043d\u0438\u044f<\/h3>\n<ul>\n<li>\n<p>\u0411\u0430\u0437\u043e\u0432\u044b\u0435 \u0437\u043d\u0430\u043d\u0438\u044f \u043e \u0444\u0440\u0435\u0439\u043c\u0432\u043e\u0440\u043a\u0435.<\/p>\n<\/li>\n<li>\n<p>\u0421\u0432\u0435\u0436\u0438\u0439 \u043f\u0440\u043e\u0435\u043a\u0442 Laravel.<\/p>\n<\/li>\n<\/ul>\n<p>\u0412 \u043e\u0431\u0449\u0435\u043c, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0441\u0442\u043e \u043d\u0430\u0447\u043d\u0435\u043c.<\/p>\n<h3>\u041a\u043e\u043d\u0442\u0435\u043a\u0441\u0442<\/h3>\n<p>\u0412 \u044d\u0442\u043e\u0439 \u0441\u0442\u0430\u0442\u044c\u0435 \u0438, \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e, \u0432 \u0441\u0435\u0440\u0438\u0438 \u0441\u0442\u0430\u0442\u0435\u0439 \u044f \u0431\u0443\u0434\u0443 \u0441\u043e\u0437\u0434\u0430\u0432\u0430\u0442\u044c API \u0434\u043b\u044f \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f \u043f\u043e \u043d\u0435\u0434\u0432\u0438\u0436\u0438\u043c\u043e\u0441\u0442\u0438.<\/p>\n<p>\u0422\u0430\u0431\u043b\u0438\u0446\u0430 <code>properties<\/code>:<\/p>\n<ul>\n<li>\n<p>id (\u0438\u0434\u0435\u043d\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440): \u043f\u0435\u0440\u0432\u0438\u0447\u043d\u044b\u0439 \u043a\u043b\u044e\u0447;<\/p>\n<\/li>\n<li>\n<p>type (\u0442\u0438\u043f): \u0441\u0442\u0440\u043e\u043a\u0430 (\u043f\u043e\u0437\u0436\u0435 \u043c\u044b, \u0432\u0435\u0440\u043e\u044f\u0442\u043d\u043e, \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u0441\u0432\u044f\u0437\u044c \u0441 &#8216;property_types&#8217;);<\/p>\n<\/li>\n<li>\n<p>price (\u0446\u0435\u043d\u0430): \u043f\u043e\u043b\u043e\u0436\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0435 \u0446\u0435\u043b\u043e\u0435 \u0447\u0438\u0441\u043b\u043e;<\/p>\n<\/li>\n<li>\n<p>description (\u043e\u043f\u0438\u0441\u0430\u043d\u0438\u0435): \u0442\u0435\u043a\u0441\u0442.<\/p>\n<\/li>\n<\/ul>\n<p>\u041f\u0440\u0438 \u0440\u0430\u0431\u043e\u0442\u0435 \u0441 Laravel \u043c\u044b \u043e\u0431\u044b\u0447\u043d\u043e \u0441\u043b\u0435\u0434\u0443\u0435\u043c \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443\/\u0441\u043e\u0433\u043b\u0430\u0448\u0435\u043d\u0438\u044e, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u043e\u0440\u0433\u0430\u043d\u0438\u0437\u0430\u0446\u0438\u0438 \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0439 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440\u0430 \u0432 5 \u043c\u0435\u0442\u043e\u0434\u0430\u0445 API:<\/p>\n<ul>\n<li>\n<p>index (\u0438\u043d\u0434\u0435\u043a\u0441);<\/p>\n<\/li>\n<li>\n<p>store (\u0445\u0440\u0430\u043d\u0435\u043d\u0438\u0435);<\/p>\n<\/li>\n<li>\n<p>update (\u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u0435);<\/p>\n<\/li>\n<li>\n<p>delete (\u0443\u0434\u0430\u043b\u0435\u043d\u0438\u0435).<\/p>\n<\/li>\n<\/ul>\n<p>\u041c\u044b \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e \u043f\u0440\u043e\u0440\u0430\u0431\u043e\u0442\u0430\u0435\u043c \u0432\u0435\u0441\u044c \u043d\u0430\u0448 \u0441\u043f\u0438\u0441\u043e\u043a \u0438 \u043e\u0431\u044a\u044f\u0441\u043d\u0438\u043c, \u043a\u0430\u043a\u0438\u0435 \u0432\u0435\u0449\u0438 \u043d\u0430\u0438\u0431\u043e\u043b\u0435\u0435 \u0438\u043d\u0442\u0435\u0440\u0435\u0441\u043d\u044b \u0434\u043b\u044f \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f.<\/p>\n<h3>\u0422\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 Index<\/h3>\n<p>\u041c\u0435\u0442\u043e\u0434 Index \u043e\u0431\u044b\u0447\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f \u0434\u043b\u044f \u0432\u043e\u0437\u0432\u0440\u0430\u0442\u0430 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043d\u043e\u0439 <a href=\"https:\/\/laravel.com\/docs\/8.x\/collections\">\u041a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u0438<\/a> \u0434\u043b\u044f \u041c\u043e\u0434\u0435\u043b\u0438.<\/p>\n<h3>\u041f\u0440\u043e\u0432\u0435\u0434\u0435\u043c \u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435:<\/h3>\n<ul>\n<li>\n<p>\u0423 \u043d\u0430\u0441 \u0435\u0441\u0442\u044c \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0439 \u044d\u043d\u0434\u043f\u043e\u0439\u043d\u0442 API \u0434\u043b\u044f \u043f\u043e\u043b\u0443\u0447\u0435\u043d\u0438\u044f \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u0438 \u0440\u0435\u0441\u0443\u0440\u0441\u043e\u0432.<\/p>\n<\/li>\n<li>\n<p>\u041f\u0440\u043e\u0432\u0435\u0440\u0438\u043c, \u0447\u0442\u043e \u043e\u0442\u0432\u0435\u0442 \u043f\u0440\u0438\u0445\u043e\u0434\u0438\u0442 \u0432 \u0432\u0438\u0434\u0435 \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u0438.<\/p>\n<\/li>\n<\/ul>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u0442\u0435\u0441\u0442\u0430, \u043e\u0442\u043a\u0440\u043e\u0435\u043c \u0442\u0435\u0440\u043c\u0438\u043d\u0430\u043b \u0432\u043d\u0443\u0442\u0440\u0438 \u0432\u0430\u0448\u0435\u0433\u043e \u043f\u0440\u043e\u0435\u043a\u0442\u0430 Laravel \u0438 \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0435\u0433\u043e:<\/p>\n<pre><code>php artisan make:test Api\/PropertiesTest<\/code><\/pre>\n<p>\u042d\u0442\u043e \u0441\u043e\u0437\u0434\u0430\u0441\u0442 \u0444\u0430\u0439\u043b \u0442\u0435\u0441\u0442\u0430 \u0432 <code>\/tests\/Features\/Api\/PropertiesTest.php<\/code><\/p>\n<p>\u0412\u043d\u0443\u0442\u0440\u0438 \u044d\u0442\u043e\u0433\u043e \u0444\u0430\u0439\u043b\u0430 \u043c\u044b \u0434\u043e\u0431\u0430\u0432\u0438\u043c \u043d\u0430\u0448 \u043f\u0435\u0440\u0432\u044b\u0439 \u0442\u0435\u0441\u0442, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0442\u044c, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043f\u0430\u043b\u0438 \u0432 \u043c\u0430\u0440\u0448\u0440\u0443\u0442 API <code>index<\/code> \u0438 \u043f\u043e\u043b\u0443\u0447\u0438\u043b\u0438 \u043e\u0431\u0440\u0430\u0442\u043d\u043e \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u044e \u0441\u0432\u043e\u0439\u0441\u0442\u0432 (Properties), \u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u043d\u0430 \u0434\u0430\u043d\u043d\u044b\u0439 \u043c\u043e\u043c\u0435\u043d\u0442 \u0443 \u043d\u0430\u0441 \u043d\u0435\u0442, \u043d\u043e \u044f \u043f\u043e\u0437\u0432\u043e\u043b\u044e \u0442\u0435\u0441\u0442\u0443 \u0441\u0430\u043c\u043e\u043c\u0443 \u043f\u043e\u0440\u0443\u043b\u0438\u0442\u044c.<\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Feature\\Api;      use Tests\\TestCase; use Illuminate\\Foundation\\Testing\\RefreshDatabase;      class PropertiesTest extends TestCase   { use RefreshDatabase;  \/** @test *\/ public function can_get_all_properties() { \/\/ Create Property so that the response returns it. $property = Property::factory()->create();  $response = $this->getJson(route('api.properties.index')); \/\/ We will only assert that the response returns a 200 status for now. $response->assertOk();  } }<\/code><\/pre>\n<p>\u041a\u043e\u043d\u0435\u0447\u043d\u043e, \u0437\u0434\u0435\u0441\u044c \u0432\u043e\u0437\u043d\u0438\u043a\u043d\u0435\u0442 \u043e\u0448\u0438\u0431\u043a\u0430, \u043c\u044b \u0435\u0449\u0435 \u043d\u0435 \u0441\u043e\u0437\u0434\u0430\u043b\u0438 \u043c\u043e\u0434\u0435\u043b\u044c <code>Property<\/code>, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043f\u043e\u0441\u043b\u0435 \u0437\u0430\u043f\u0443\u0441\u043a\u0430 <code>.\/vendor\/bin\/phpunit --testdox<\/code> \u0432 \u043a\u0430\u0442\u0430\u043b\u043e\u0433\u0435 \u043d\u0430\u0448\u0435\u0433\u043e \u043f\u0440\u043e\u0435\u043a\u0442\u0430 \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u043c:<\/p>\n<pre><code class=\"php\">Tests\\Feature\\Api\\PropertiesTest::can_get_all_properties Error: Class 'Tests\\Feature\\Api\\Property' not found<\/code><\/pre>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e:<\/p>\n<p><code>php artisan make:model Property -mf<\/code><\/p>\n<p>\u041f\u0440\u0438\u0432\u0435\u0434\u0435\u043d\u043d\u0430\u044f \u0432\u044b\u0448\u0435 \u043a\u043e\u043c\u0430\u043d\u0434\u0430 \u0432\u044b\u043f\u043e\u043b\u043d\u0438\u0442:<\/p>\n<ul>\n<li>\n<p>\u0421\u043e\u0437\u0434\u0430\u0441\u0442 \u043c\u043e\u0434\u0435\u043b\u044c, \u0440\u0430\u0441\u043f\u043e\u043b\u043e\u0436\u0435\u043d\u043d\u0443\u044e \u0432 <code>app\/Models\/Property.php<\/code><\/p>\n<\/li>\n<li>\n<p><code>-m<\/code> \u0441\u043e\u0437\u0434\u0430\u0441\u0442 \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u044e \u0432 <code>\/database\/migrations\/<\/code><\/p>\n<\/li>\n<li>\n<p><code>-f<\/code> \u0441\u043e\u0437\u0434\u0430\u0441\u0442 \u043a\u043b\u0430\u0441\u0441 Factory (\u0444\u0430\u0431\u0440\u0438\u043a\u0430) \u0432 <code>\/database\/factories\/PropertyFactory<\/code>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043c\u044b \u0431\u0443\u0434\u0435\u043c \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0434\u043b\u044f \u043c\u043e\u043a\u0438\u043d\u0433\u0430 &#171;Property&#187; \u0438 \u0435\u0433\u043e \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u043e\u0432.<\/p>\n<\/li>\n<\/ul>\n<p>\u041f\u0440\u0438\u043c\u0435\u043d\u044f\u044f TDD, \u0434\u0435\u0439\u0441\u0442\u0432\u0443\u0435\u043c \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e; \u043f\u043e\u0441\u043b\u0435 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u043d\u0430\u0448\u0435\u0439 \u043c\u043e\u0434\u0435\u043b\u0438, \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u0438 \u0438 \u0444\u0430\u0431\u0440\u0438\u043a\u0438 \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0442\u0435\u0441\u0442 \u0441\u043d\u043e\u0432\u0430 (\u0432\u044b \u043f\u043e\u043b\u0443\u0447\u0438\u0442\u0435 \u0442\u0443 \u0436\u0435 \u043e\u0448\u0438\u0431\u043a\u0443, \u0435\u0441\u043b\u0438 \u043d\u0435 \u0438\u043c\u043f\u043e\u0440\u0442\u0438\u0440\u0443\u0435\u0442\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u043c\u043e\u0434\u0435\u043b\u0438 Property \u043f\u043e\u0432\u0435\u0440\u0445 \u0432\u0430\u0448\u0435\u0433\u043e \u0442\u0435\u0441\u0442\u0430):<\/p>\n<pre><code>Tests\\Feature\\Api\\PropertiesTest::can_get_all_properties Symfony\\Component\\Routing\\Exception\\RouteNotFoundException:  Route [api.properties.index] not defined.<\/code><\/pre>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0438 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u044b\u0439 \u044d\u043d\u0434\u043f\u043e\u0439\u043d\u0442 \u0432 \u0444\u0430\u0439\u043b\u0435 <code>\/routes\/api.php<\/code>:<\/p>\n<pre><code class=\"php\">use App\\Http\\Controllers\\Api\\PropertyController;  Route::get( 'properties',  [PropertyController::class, 'index'] )->name('api.properties.index');<\/code><\/pre>\n<p>\u0414\u0430\u043b\u0435\u0435 \u043c\u044b \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0435\u0433\u043e \u0438 \u043f\u043e\u043b\u0443\u0447\u0438\u043c \u043e\u0448\u0438\u0431\u043a\u0443; <code>PropertyController<\/code> \u043d\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442:<\/p>\n<p><code>ReflectionException: Class PropertyController does not exist<\/code><\/p>\n<p>\u041e\u0442\u043a\u0440\u043e\u0435\u043c \u0442\u0435\u0440\u043c\u0438\u043d\u0430\u043b \u0438 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u043d\u0430\u0448 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440 \u0447\u0435\u0440\u0435\u0437 artisan:<\/p>\n<pre><code>php artisan make:controller Api\/PropertyController<\/code><\/pre>\n<p>\u041a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440 \u0431\u0443\u0434\u0435\u0442 \u0440\u0430\u0441\u043f\u043e\u043b\u043e\u0436\u0435\u043d \u0432 <code>\/app\/Http\/Controllers\/Api\/PropertyController.php<\/code> .<\/p>\n<p>\u041e\u0442\u043a\u0440\u043e\u0439\u0442\u0435 \u0440\u0430\u043d\u0435\u0435 \u0441\u043e\u0437\u0434\u0430\u043d\u043d\u044b\u0439 \u0444\u0430\u0439\u043b \u0438 \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u0435 \u0442\u0435\u0441\u0442 \u0441\u043d\u043e\u0432\u0430:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use Illuminate\\Http\\Request;   use App\\Http\\Controllers\\Controller;      class PropertyController extends Controller   {       }<\/code><\/pre>\n<p>\u041c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0435\u0449\u0435 \u043e\u0434\u043d\u0443 \u043e\u0448\u0438\u0431\u043a\u0443, \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u044e\u0449\u0443\u044e \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u043c\u0435\u0442\u043e\u0434 <code>index<\/code> \u043d\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u0435\u0433\u043e, \u0447\u0442\u043e\u0431\u044b, \u043d\u0430\u043a\u043e\u043d\u0435\u0446, \u0434\u043e\u0431\u0438\u0442\u044c\u0441\u044f \u043f\u0440\u043e\u0445\u043e\u0436\u0434\u0435\u043d\u0438\u044f \u0442\u0435\u0441\u0442\u0430:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use Illuminate\\Http\\Request;   use App\\Http\\Controllers\\Controller;      class PropertyController extends Controller   {   public function index() { } }<\/code><\/pre>\n<p>\u0417\u0430\u043f\u0443\u0441\u043a\u0430\u0435\u043c \u0442\u0435\u0441\u0442, \u0438 \u043e\u043d \u043f\u0440\u043e\u0445\u043e\u0434\u0438\u0442, \u043d\u043e&#8230; \u043c\u044b \u043d\u0435 \u0432\u044b\u043f\u043e\u043b\u043d\u0438\u043b\u0438 \u0444\u0430\u043a\u0442\u0438\u0447\u0435\u0441\u043a\u0443\u044e \u043b\u043e\u0433\u0438\u043a\u0443, \u0447\u0442\u043e\u0431\u044b \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c, \u0447\u0442\u043e \u043e\u043d \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u044e, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e, \u043e\u0431\u043d\u043e\u0432\u0438\u0432 \u043d\u0430\u0448 \u0442\u0435\u0441\u0442, \u0447\u0442\u043e\u0431\u044b \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0430\u0442\u044c, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c JSON.<\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Feature\\Api;      use Tests\\TestCase; use Illuminate\\Foundation\\Testing\\RefreshDatabase;      class PropertiesTest extends TestCase   { use RefreshDatabase;  \/** @test *\/ public function can_get_all_properties() { \/\/ Create Property so that the response returns it. $property = Property::factory()->create();  $response = $this->getJson(route('api.properties.index')); \/\/ We will only assert that the response returns a 200  \/\/ status for now. $response->assertOk();   \/\/ Add the assertion that will prove that we receive what we need  \/\/ from the response. $response->assertJson([ 'data' => [ [ 'id' => $property->id, 'type' => $property->type,   'price' => $property->price,   'description' => $property->description, ] ] ]); } }<\/code><\/pre>\n<p>\u0418, \u043a\u043e\u043d\u0435\u0447\u043d\u043e \u0436\u0435, \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c:<\/p>\n<p><code>Invalid JSON was returned from the route<\/code><strong>.<\/strong> (\u0441 \u043c\u0430\u0440\u0448\u0440\u0443\u0442\u0430 \u0431\u044b\u043b \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0435\u043d \u043d\u0435\u0434\u043e\u043f\u0443\u0441\u0442\u0438\u043c\u044b\u0439 JSON), \u043d\u0443&#8230; \u043c\u044b \u043d\u0430 \u0441\u0430\u043c\u043e\u043c \u0434\u0435\u043b\u0435 \u043d\u0438\u0447\u0435\u0433\u043e \u043d\u0435 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c \u0438\u0437 \u043c\u0435\u0442\u043e\u0434\u0430 <code>index<\/code>, \u0442\u0430\u043a \u0447\u0442\u043e \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u0441\u0434\u0435\u043b\u0430\u0435\u043c \u044d\u0442\u043e:<\/p>\n<pre><code class=\"php\">&lt;?php      namespace App\\Http\\Controllers\\Api;      use App\\Models\\Property; use Illuminate\\Http\\Request;   use App\\Http\\Controllers\\Controller;      class PropertyController extends Controller   {   public function index() { return response()->json([       'data' => Property::all()   ]); } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u0447\u0438\u043d\u0430, \u043f\u043e \u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u043c\u044b \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c \u043c\u0430\u0441\u0441\u0438\u0432 <code>data<\/code> \u0438 \u0432\u043d\u0443\u0442\u0440\u0438 \u043d\u0435\u0433\u043e \u043a\u043e\u043b\u043b\u0435\u043a\u0446\u0438\u044e, \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0435 \u043e\u0442\u0432\u0435\u0442\u043e\u0432 API, \u0433\u0434\u0435 \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u043c\u043e\u0435 \u0434\u043e\u043b\u0436\u043d\u043e \u0431\u044b\u0442\u044c \u0432\u043d\u0443\u0442\u0440\u0438 \u044d\u0442\u043e\u0433\u043e \u043c\u0430\u0441\u0441\u0438\u0432\u0430 <code>data<\/code>.<\/p>\n<p>\u041c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0435\u0449\u0435 \u043e\u0434\u043d\u0443 \u043e\u0448\u0438\u0431\u043a\u0443, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u0438, \u0447\u0442\u043e \u043c\u044b \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b Property, \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0435\u043d\u043d\u044b\u0435 \u0438\u0437 \u043e\u0442\u0432\u0435\u0442\u0430, \u043d\u043e \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b \u044f\u0432\u043b\u044f\u044e\u0442\u0441\u044f <code>null<\/code>, \u043c\u043e\u0436\u0435\u0442\u0435 \u0441\u0435\u0431\u0435 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u0438\u0442\u044c, \u043f\u043e\u0447\u0435\u043c\u0443?<\/p>\n<pre><code class=\"php\">Unable to find JSON:   [{     \"data\": [         {             \"id\": 1,             \"type\": null,             \"price\": null,             \"description\": null         }     ] }]  within response JSON:  [{     \"data\": [         {             \"id\": 1,             \"created_at\": \"2021-10-15T14:44:21.000000Z\",             \"updated_at\": \"2021-10-15T14:44:21.000000Z\"         }     ] }]<\/code><\/pre>\n<p>\u0412\u044b \u0443\u0433\u0430\u0434\u0430\u043b\u0438! \u041c\u044b \u043d\u0435 \u043e\u0431\u043d\u043e\u0432\u0438\u043b\u0438 \u043d\u0430\u0448 \u043a\u043b\u0430\u0441\u0441 PropertyFactory, \u0447\u0442\u043e\u0431\u044b \u043e\u043d \u0438\u043c\u0435\u043b \u0437\u0430\u043f\u043b\u0430\u043d\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \u043d\u0430\u043c\u0438 \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b:<\/p>\n<pre><code class=\"php\">use App\\Models\\Property;   use Illuminate\\Database\\Eloquent\\Factories\\Factory;  class PropertyFactory extends Factory   {    \/**    * The name of the factory's corresponding model. * * @var string    *\/    protected $model = Property::class;     \/**    * Define the model's default state.       * @return array    *\/    public function definition()    {  return [   'type' => $this->faker->word,   'price' => $this->faker->randomNumber(6),   'description' => $this->faker->paragraph,  ];    }  }<\/code><\/pre>\n<p>\u041c\u044b \u043d\u0430\u0447\u043d\u0435\u043c \u043f\u043e\u043b\u0443\u0447\u0430\u0442\u044c \u043e\u0448\u0438\u0431\u043a\u0438, \u0441\u0432\u044f\u0437\u0430\u043d\u043d\u044b\u0435 \u0441 &#171;\u043d\u0435\u0438\u0437\u0432\u0435\u0441\u0442\u043d\u044b\u043c\u0438 \u0441\u0442\u043e\u043b\u0431\u0446\u0430\u043c\u0438&#8230;&#187;. \u043f\u043e\u0442\u043e\u043c\u0443 \u0447\u0442\u043e \u043d\u0430\u0448\u0430 \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u044f \u043d\u0435 \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442 \u0441\u0442\u043e\u043b\u0431\u0446\u043e\u0432, \u043a\u043e\u0442\u043e\u0440\u044b\u0435, \u043f\u043e \u043d\u0430\u0448\u0435\u043c\u0443 \u0443\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u044e, \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0442.<\/p>\n<p>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043e\u0431\u043d\u043e\u0432\u0438\u043c \u043c\u0438\u0433\u0440\u0430\u0446\u0438\u044e, \u0434\u043e\u0431\u0430\u0432\u0438\u0432 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u044b\u0435 \u0441\u0442\u043e\u043b\u0431\u0446\u044b:<\/p>\n<pre><code class=\"php\">Schema::create('properties', function (Blueprint $table) {   $table->id();   $table->string('type', 20); $table->unsignedInteger('price'); $table->text('description'); $table->timestamps();   });<\/code><\/pre>\n<p>\u0415\u0441\u043b\u0438 \u043c\u044b \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u043c \u0442\u0435\u0441\u0442 \u0441\u043d\u043e\u0432\u0430, \u0442\u043e \u0437\u0430\u043c\u0435\u0442\u0438\u043c, \u0447\u0442\u043e \u043e\u043d \u0441\u043d\u043e\u0432\u0430 \u043f\u0440\u043e\u0448\u0435\u043b, \u0438 \u043d\u0430 \u044d\u0442\u043e\u0442 \u0440\u0430\u0437 \u043e\u043a\u043e\u043d\u0447\u0430\u0442\u0435\u043b\u044c\u043d\u043e.<\/p>\n<p>\u0422\u0435\u043f\u0435\u0440\u044c, \u043a\u043e\u0433\u0434\u0430 \u043c\u044b \u0441\u043e\u0437\u0434\u0430\u043b\u0438 \u043f\u0440\u043e\u0442\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0439 \u043c\u0435\u0442\u043e\u0434 <code>index<\/code>, \u0434\u0430\u0432\u0430\u0439\u0442\u0435 \u043f\u0440\u043e\u0434\u043e\u043b\u0436\u0438\u043c \u0441 \u043c\u0435\u0442\u043e\u0434\u043e\u043c Store, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043f\u043e\u0442\u0440\u0435\u0431\u0443\u0435\u0442 \u043d\u0435\u043c\u043d\u043e\u0433\u043e \u0431\u043e\u043b\u044c\u0448\u0435 \u0440\u0430\u0431\u043e\u0442\u044b.<\/p>\n<h3>\u0422\u0435\u0441\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043c\u0435\u0442\u043e\u0434\u0430 Store<\/h3>\n<p>\u042d\u0442\u043e\u0442 \u0442\u0435\u0441\u0442 \u043c\u044b \u043d\u0430\u0447\u043d\u0435\u043c \u0441 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u0432\u0442\u043e\u0440\u043e\u0433\u043e \u0442\u0435\u0441\u0442\u0430 \u0432 \u0442\u043e\u043c \u0436\u0435 \u0444\u0430\u0439\u043b\u0435 <code>tests\/Feature\/Api\/PropertiesTest.php<\/code><\/p>\n<pre><code class=\"php\">&lt;?php      namespace Tests\\Feature\\Api;      use Tests\\TestCase; use Illuminate\\Foundation\\Testing\\RefreshDatabase;      class PropertiesTest extends TestCase   { use RefreshDatabase;  \/** @test *\/   public function can_get_all_properties(){...}  \/** @test *\/ \/** @test *\/     public function can_store_a_property()     {         \/\/ Build a non-persisted Property factory model.         $newProperty = Property::factory()->make();          $response = $this->postJson(             route('api.properties.store'),             $newProperty->toArray()         );         \/\/ We assert that we get back a status 201:         \/\/ Resource Created for now.         $response->assertCreated();         \/\/ Assert that at least one column gets returned from the response         \/\/ in the format we need .         $response->assertJson([              'data' => ['type' =><\/code><\/pre>\n<\/div>\n<\/div>\n<\/div>\n<\/div>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[],"tags":[],"class_list":["post-335184","post","type-post","status-publish","format-standard","hentry"],"_links":{"self":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts\/335184","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=335184"}],"version-history":[{"count":0,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts\/335184\/revisions"}],"wp:attachment":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=335184"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=335184"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=335184"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}