{ "uuid": [ { "value": "066297b1-ab00-4769-afe1-d3831ed2a654" } ], "langcode": [ { "value": "en" } ], "type": [ { "target_id": "daily_email", "target_type": "node_type", "target_uuid": "8bde1f2f-eef9-4f2d-ae9c-96921f8193d7" } ], "revision_timestamp": [ { "value": "2025-05-11T09:00:12+00:00" } ], "revision_uid": [ { "target_type": "user", "target_uuid": "b8966985-d4b2-42a7-a319-2e94ccfbb849" } ], "revision_log": [], "status": [ { "value": true } ], "uid": [ { "target_type": "user", "target_uuid": "b8966985-d4b2-42a7-a319-2e94ccfbb849" } ], "title": [ { "value": "Writing assertions first" } ], "created": [ { "value": "2024-06-05T00:00:00+00:00" } ], "changed": [ { "value": "2025-05-11T09:00:12+00:00" } ], "promote": [ { "value": false } ], "sticky": [ { "value": false } ], "default_langcode": [ { "value": true } ], "revision_translation_affected": [ { "value": true } ], "path": [ { "alias": "\/daily\/2024\/06\/05\/writing-assertions-first", "langcode": "en" } ], "body": [ { "value": "\n

As well as writing comments first<\/a>, when writing tests, I sometimes like to write my tests backwards and start by writing the assertions first.<\/p>\n\n

I know what I want to assert in the test, so it's an easy place to start.<\/p>\n\n

I'll run it, see the error, fix it and continue working backwards.<\/p>\n\n

For example, I could start with this:<\/p>\n\n

public function testOnlyPostNodesAreShown(): void {\n  $assert = $this->assertSession();\n  $assert->pageTextContains('Post one');\n  $assert->pageTextContains('Post two');\n  $assert->pageTextNotContains('This is not a post');\n}\n<\/code><\/pre>\n\n

This test will fail when I run it, but it makes me think about what I need to do to fix the error and how to do so in the best way.<\/p>\n\n

In this case, I need to make a request to the page that should render the text:<\/p>\n\n

public function testOnlyPostNodesAreShown(): void {\n  $this->drupalGet('\/blog');\n\n  $assert = $this->assertSession();\n  $assert->pageTextContains('Post one');\n  $assert->pageTextContains('Post two');\n  $assert->pageTextNotContains('This is not a post');\n}\n<\/code><\/pre>\n\n

This will still fail, as I also need to create the required posts:<\/p>\n\n

public function testOnlyPostNodesAreShown(): void {\n  PostBuilder::create()->setTitle('Post one')->getPost();\n  PostBuilder::create()->setTitle('Post two')->getPost();\n\n  $this->createNode([\n    'title' => 'This is not a post',\n    'type' => 'page',\n  ]);\n\n  $this->drupalGet('\/blog');\n\n  $assert = $this->assertSession();\n  $assert->pageTextContains('Post one');\n  $assert->pageTextContains('Post two');\n  $assert->pageTextNotContains('This is not a post');\n}\n<\/code><\/pre>\n\n

Now the test passes.<\/p>\n\n

Doing test-driven development keeps my code clean and minimal, and I find this approach keeps my test clean, too.<\/p>\n\n ", "format": "full_html", "processed": "\n

As well as writing comments first<\/a>, when writing tests, I sometimes like to write my tests backwards and start by writing the assertions first.<\/p>\n\n

I know what I want to assert in the test, so it's an easy place to start.<\/p>\n\n

I'll run it, see the error, fix it and continue working backwards.<\/p>\n\n

For example, I could start with this:<\/p>\n\n

public function testOnlyPostNodesAreShown(): void {\n  $assert = $this->assertSession();\n  $assert->pageTextContains('Post one');\n  $assert->pageTextContains('Post two');\n  $assert->pageTextNotContains('This is not a post');\n}\n<\/code><\/pre>\n\n

This test will fail when I run it, but it makes me think about what I need to do to fix the error and how to do so in the best way.<\/p>\n\n

In this case, I need to make a request to the page that should render the text:<\/p>\n\n

public function testOnlyPostNodesAreShown(): void {\n  $this->drupalGet('\/blog');\n\n  $assert = $this->assertSession();\n  $assert->pageTextContains('Post one');\n  $assert->pageTextContains('Post two');\n  $assert->pageTextNotContains('This is not a post');\n}\n<\/code><\/pre>\n\n

This will still fail, as I also need to create the required posts:<\/p>\n\n

public function testOnlyPostNodesAreShown(): void {\n  PostBuilder::create()->setTitle('Post one')->getPost();\n  PostBuilder::create()->setTitle('Post two')->getPost();\n\n  $this->createNode([\n    'title' => 'This is not a post',\n    'type' => 'page',\n  ]);\n\n  $this->drupalGet('\/blog');\n\n  $assert = $this->assertSession();\n  $assert->pageTextContains('Post one');\n  $assert->pageTextContains('Post two');\n  $assert->pageTextNotContains('This is not a post');\n}\n<\/code><\/pre>\n\n

Now the test passes.<\/p>\n\n

Doing test-driven development keeps my code clean and minimal, and I find this approach keeps my test clean, too.<\/p>\n\n ", "summary": null } ] }