diff --git a/functions.js b/functions.js
index d0245836b617e54b611c0569562f6027a7e310ae..00790128568858c07e4ba539dc88d2be215a2878 100644
--- a/functions.js
+++ b/functions.js
@@ -77,7 +77,7 @@ function createNewsChild(news) {
     a.appendChild(textNode);
 
     const hrefAttr = document.createAttribute('href');
-    hrefAttr.value = '#';
+    hrefAttr.value = 'NewsArticle.php?articleId=' + encodeURIComponent(news['id']);
 
     a.setAttributeNode(hrefAttr);
 
diff --git a/php/Index.php b/php/Index.php
index fbe42a089f22921687b4f7df5f8b465173eee767..4ae99fad54c1176cbae068d569a8382024e6c466 100644
--- a/php/Index.php
+++ b/php/Index.php
@@ -40,13 +40,15 @@ class Index extends Page {
             $news[] = new News($title, $imgurl, $content);  
         } 
 
+        $resultSet->close();
+
         return $news;
     }
 
     protected function generateView():void
     {
 		$this->news = $this->getViewData();
-        $this->generatePageHeader('NASA');
+        $this->generatePageHeader('NASA', '../functions.js');
         
         echo <<<EOT
 
diff --git a/php/NewsArticle.php b/php/NewsArticle.php
new file mode 100644
index 0000000000000000000000000000000000000000..fba88a42921f97d8839932b0c45a66775d81902f
--- /dev/null
+++ b/php/NewsArticle.php
@@ -0,0 +1,94 @@
+<?php declare(strict_types=1);
+
+require_once 'Page.php';
+
+class NewsArticle extends Page
+{
+    private const ARTICLE_ID = 'articleId';
+
+    private const TITLE = 'title';
+    private const IMGURL = 'imgurl';
+    private const CONTENT = 'content';
+
+    private int $articleId;
+
+    protected function __construct()
+    {
+        parent::__construct();
+
+        $this->articleId = -1;
+
+        session_start();
+    }
+
+    public function __destruct()
+    {
+        parent::__destruct();
+    }
+
+    protected function getViewData():array
+    {
+        $stmt = $this->database->prepare("SELECT n.title, n.imgurl, n.content FROM news n WHERE n.id = ?");
+        $stmt->bind_param("i", $this->articleId);
+        $stmt->execute();
+
+        $resultSet = $stmt->get_result();
+
+        if ($resultSet->num_rows == 0) 
+            return array();
+
+        $article = $resultSet->fetch_assoc();
+
+        $array = array(
+            self::TITLE => $article[self::TITLE],
+            self::IMGURL => $article[self::IMGURL],
+            self::CONTENT => $article[self::CONTENT]
+        );
+        
+        $resultSet->free();
+        $stmt->close();
+
+		return $array;
+    }
+
+    protected function generateView():void
+    {
+		$data = $this->getViewData();
+        $this->generatePageHeader('News Article');
+
+        var_dump($data);
+
+        echo <<<EOT
+<body>
+        <header></header>
+</body>
+EOT;
+
+        $this->generatePageFooter();
+    }
+
+    protected function processReceivedData():void
+    {
+        parent::processReceivedData();
+
+        if ($_SERVER['REQUEST_METHOD'] === 'GET') {
+            if (isset($_GET[self::ARTICLE_ID]) && is_numeric($_GET[self::ARTICLE_ID])) {
+                $this->articleId = intval($_GET[self::ARTICLE_ID]);
+            }
+        }
+    }
+
+    public static function main():void
+    {
+        try {
+            $page = new NewsArticle();
+            $page->processReceivedData();
+            $page->generateView();
+        } catch (Exception $e) {
+            header("Content-type: text/html; charset=UTF-8");
+            echo $e->getMessage();
+        }
+    }
+}
+
+NewsArticle::main();
\ No newline at end of file
diff --git a/php/NewsFetch.php b/php/NewsFetch.php
index d8db0e2f1af831a90d9e3cec5d009d54ab8d3dba..ce569b31c31a536d59b925ba91e5e0ab3684fced 100644
--- a/php/NewsFetch.php
+++ b/php/NewsFetch.php
@@ -5,6 +5,7 @@ require_once 'util/constants.php';
 
 class NewsFetch extends Page
 {
+    private const ID = "id";
     private const TITLE = "title";
     private const SEARCH_WORD = "searchWord";
 
@@ -31,15 +32,16 @@ class NewsFetch extends Page
 
         $likeSearchWord = "%" . $this->searchWord . "%";
 
-		$stmt = $this->database->prepare("SELECT n.title FROM news n WHERE LOWER(n.title) LIKE LOWER(?) LIMIT 5");
+		$stmt = $this->database->prepare("SELECT n.id, n.title FROM news n WHERE LOWER(n.title) LIKE LOWER(?) LIMIT 5");
         $stmt->bind_param("s", $likeSearchWord);
         $stmt->execute();
         $resultSet = $stmt->get_result();
 
         while($row = $resultSet->fetch_assoc()) {
+            $id = $row[self::ID];
             $title = $row[self::TITLE];
 
-            $data[] = array(self::TITLE => $title); 
+            $data[] = array(self::ID => $id, self::TITLE => $title); 
         }
 
         return $data;
diff --git a/php/Page.php b/php/Page.php
index c56d9d5988aef0d9e2ba2f50247c956240f36257..18ba86408e4c90c464767cf185cff372028b77b2 100644
--- a/php/Page.php
+++ b/php/Page.php
@@ -25,7 +25,7 @@ abstract class Page {
         /*$this->database->close();*/
     }
 
-    protected function generatePageHeader(string $title = ""):void
+    protected function generatePageHeader(string $title = "", string $jsScript = ""):void
     {
         $title = htmlspecialchars($title);
         header("Content-type: text/html; charset=UTF-8");
@@ -37,7 +37,11 @@ abstract class Page {
     <title>$title</title>
     <meta charset="UTF-8" />
     <meta name="viewport" content="width=device-width, initial-scale=1">
-    <script src="../functions.js"></script>
+EOT;
+        if (!empty(trim($jsScript)))
+            echo "<script src=\"$jsScript\"></script>";
+
+        echo <<<EOT
     <link rel="stylesheet" style="text/css" href="../styles.css" />
 </head>
 EOT;