diff --git a/amp.admin.inc b/amp.admin.inc
index b272f1f..098dfd2 100644
--- a/amp.admin.inc
+++ b/amp.admin.inc
@@ -42,6 +42,18 @@ function amp_admin_form($form, &$form_state) {
     );
   }
 
+  $form['amp_url_format'] = array(
+    '#type' => 'radios',
+    '#title' => t('URL format'),
+    '#default_value' => variable_get('amp_url_format', 'query_string'),
+    '#options' => array(
+      'query_string' => 'Query string (www.example.com/article?amp)',
+      'prefix' => 'Path prefix (www.example.com/amp/article)',
+      'suffix' => 'Path suffix (www.example.com/article/amp)',
+    ),
+    '#description' => t('Choose how your amp urls look.'),
+  );
+
   // AMP theme settings.
   $form['amp_theme'] = array(
     '#type' => 'select',
@@ -174,14 +186,14 @@ function amp_admin_form($form, &$form_state) {
 /**
  * Submit handler for the amp_admin_form
  * Clears the Drupal cache if the AMP Library warnings display checkbox value is changed
- * 
+ *
  * @param type $form
  * @param type $form_state
  */
 function amp_admin_form_submit($form, &$form_state) {
   if (variable_get('amp_library_warnings_display', false) !== $form_state['values']['amp_library_warnings_display']) {
     cache_clear_all();
-    drupal_set_message(t('AMP Library debugging checkbox changed. Cleared cache.'));    
+    drupal_set_message(t('AMP Library debugging checkbox changed. Cleared cache.'));
   }
 }
 
diff --git a/amp.install b/amp.install
index 2a0acda..5f5509a 100644
--- a/amp.install
+++ b/amp.install
@@ -48,3 +48,11 @@ function amp_requirements($phase) {
   }
   return $requirements;
 }
+
+/**
+ * Implements hook_uninstall().
+ */
+function amp_uninstall() {
+  // Delete variables.
+  variable_del('amp_url_format');
+}
diff --git a/amp.module b/amp.module
index 717ef33..4735775 100644
--- a/amp.module
+++ b/amp.module
@@ -327,6 +327,32 @@ function amp_entity_info_alter(&$entity_info) {
 }
 
 /**
+ * Implements hook_url_inbound_alter().
+ *
+ * Rewrites the active path for AMP pages to the non-AMP path.
+ */
+function amp_url_inbound_alter(&$path, $original_path, $path_language) {
+  if (!amp_is_amp_request()) {
+    return;
+  }
+
+  switch (variable_get('amp_url_format', 'query_string')) {
+    case 'query_string':
+      return;
+    case 'suffix':
+      $non_amp_path = substr($path, 0, strlen($path) - strlen('/amp'));
+      break;
+    case 'prefix':
+      $non_amp_path = substr($path, strlen('amp/'), strlen($path));
+      break;
+  }
+  $system_path = drupal_lookup_path('source', $non_amp_path, $path_language);
+  $path = $system_path ?: $non_amp_path;
+
+  menu_set_active_item($path);
+}
+
+/**
  * Determines whether a request should return AMP HTML.
  */
 function amp_is_amp_request() {
@@ -334,18 +360,37 @@ function amp_is_amp_request() {
 
   if (!isset($result)) {
     $result = FALSE;
+    $current_path = current_path();
+
+    switch (variable_get('amp_url_format', 'query_string')) {
+      case 'query_string':
+        $is_amp_path = isset($_GET['amp']);
+        $non_amp_path = $current_path;
+        break;
+      case 'suffix':
+        $is_amp_path = substr($current_path, -strlen('/amp')) == '/amp';
+        $non_amp_path = substr($current_path, 0, strlen($current_path) - strlen('/amp'));
+        break;
+      case 'prefix':
+        $is_amp_path = substr($current_path, 0, strlen('amp/')) == 'amp/';
+        $non_amp_path = substr($current_path, strlen('amp/'), strlen($current_path));
+        break;
+    }
 
-    // The current request must have '?amp' in the query string.
-    if (isset($_GET['amp'])) {
+    // Check that the path format is a valid amp format,
+    // and that original path isn't an already registered route.
+    // @TODO These amp paths should really be registered as system routes.
+    if ($is_amp_path && !(drupal_valid_path($current_path) && $current_path !== $non_amp_path)) {
       // Ensure that there is a node loaded from the current request, and that
       // it is a node type which has the AMP view mode enabled.
-      $node = menu_get_object();
+      $non_amp_path = drupal_get_normal_path($non_amp_path);
+      $node = menu_get_object('node', 1, $non_amp_path);
       if ($node && in_array($node->type, amp_get_enabled_types())) {
         // Do an additional check to ensure the current path is actually the
         // node's public URI. Without this check, this function would return
         // TRUE on the node's edit form.
         $uri = entity_uri('node', $node);
-        if ($uri['path'] == current_path()) {
+        if ($uri['path'] == $non_amp_path) {
           // Only if all of the above conditions are true is this a valid AMP
           // request.
           $result = TRUE;
@@ -648,9 +693,20 @@ function amp_node_view($node, $view_mode, $langcode) {
   // Show amphtml links on AMP-enabled nodes so search engines can find AMP.
   if ($view_mode == 'full' && node_is_page($node) && in_array($node->type, amp_get_enabled_types())) {
     $uri = entity_uri('node', $node);
-    $uri['options']['query']['amp'] = NULL;
     $uri['options']['absolute'] = TRUE;
-    drupal_add_html_head_link(array('rel' => 'amphtml', 'href' => url($uri['path'], $uri['options'])), TRUE);
+    $alias_path = drupal_get_path_alias($uri['path']);
+    switch (variable_get('amp_url_format', 'query_string')) {
+      case 'query_string':
+        $uri['options']['query']['amp'] = NULL;
+        break;
+      case 'suffix':
+        $alias_path = $alias_path . '/amp';
+        break;
+      case 'prefix':
+        $alias_path = 'amp/' . $alias_path;
+        break;
+    }
+    drupal_add_html_head_link(array('rel' => 'amphtml', 'href' => url($alias_path, $uri['options'])), TRUE);
   }
 
   // Add AMP metadata.
diff --git a/amp.test b/amp.test
index 471628b..7006a86 100644
--- a/amp.test
+++ b/amp.test
@@ -6,6 +6,7 @@
  */
 
 class AmpTestCase extends DrupalWebTestCase {
+  protected $admin_user;
 
   public static function getInfo() {
     return array(
@@ -16,10 +17,28 @@ class AmpTestCase extends DrupalWebTestCase {
   }
 
   protected function setUp() {
-    // Enable AMP module.
-    parent::setUp('amp', 'composer_manager');
+    // Enable modules.
+    parent::setUp('field_ui', 'amp', 'composer_manager');
+
+    // Create Admin user.
+    $this->admin_user = $this->drupalCreateUser(array(
+        'access administration pages',
+        'administer content types',
+        'administer site configuration',
+        'administer fields',
+        'create article content',
+      )
+    );
+    $this->drupalLogin($this->admin_user);
+
     // Install the AMP theme.
     theme_enable(array('amptheme', 'ampsubtheme_example'));
+
+    // Enable AMP display on article content.
+    $this->drupalGet("admin/structure/types/manage/article/display");
+    $this->assertResponse(200);
+    $edit = ["view_modes_custom[amp]" => '1'];
+    $this->drupalPost(NULL, $edit, t('Save'));
   }
 
   /**
@@ -29,18 +48,11 @@ class AmpTestCase extends DrupalWebTestCase {
     global $base_url;
 
     // Login as an admin user.
-    $admin_user = $this->drupalCreateUser(array('administer content types'));
-    $this->drupalLogin($admin_user);
+    $this->drupalLogin($this->admin_user);
 
     // Create a node to test AMP metadata.
     $node = $this->drupalCreateNode(array('type' => 'article'));
 
-    // Enable AMP display on article content.
-    $this->drupalGet("admin/structure/types/manage/article/display");
-    $this->assertResponse(200);
-    $edit = ["view_modes_custom[amp]" => '1'];
-    $this->drupalPost(NULL, $edit, t('Save'));
-
     // Check the full display.
     $this->drupalGet('node/' . $node->nid);
     $this->assertResponse(200);
@@ -56,8 +68,10 @@ class AmpTestCase extends DrupalWebTestCase {
     // Configure AMP field formatters.
     $this->drupalGet('admin/structure/types/manage/article/display/amp');
     $this->assertResponse(200);
-    $edit = ["fields[field_image][type]" => 'amp_image'];
-    $edit = ["fields[body][type]" => 'amp_text'];
+    $edit = [
+      "fields[field_image][type]" => 'amp_image',
+      "fields[body][type]" => 'amp_text',
+    ];
     $this->drupalPost(NULL, $edit, t('Save'));
 
     // Check the warnfix messages.
@@ -68,3 +82,218 @@ class AmpTestCase extends DrupalWebTestCase {
     $this->assertRaw('PASS');
   }
 }
+
+class AmpTestUrlFormats extends DrupalWebTestCase {
+  protected $admin_user;
+
+  public static function getInfo() {
+    return array(
+      'name' => 'AMP Url formats',
+      'description' => 'Tests AMP pages using prefix /amp and query string ?amp.',
+      'group' => 'AMP',
+    );
+  }
+
+  protected function setUp() {
+    // Enable modules.
+    parent::setUp('field_ui', 'path', 'amp', 'composer_manager');
+
+    // Create Admin user.
+    $this->admin_user = $this->drupalCreateUser(array(
+        'create url aliases',
+        'access administration pages',
+        'administer site configuration',
+        'administer content types',
+        'administer fields',
+        'create article content',
+        'edit any article content',
+      )
+    );
+    $this->drupalLogin($this->admin_user);
+
+    // Install the AMP theme.
+    theme_enable(array('amptheme', 'ampsubtheme_example'));
+
+    // Enable AMP display on article content.
+    $this->drupalGet("admin/structure/types/manage/article/display");
+    $this->assertResponse(200);
+    $edit = ["view_modes_custom[amp]" => '1'];
+    $this->drupalPost(NULL, $edit, t('Save'));
+  }
+
+  /**
+   * Test the url with query string ?amp.
+   */
+  public function testAmpUrlFormatQueryString() {
+    global $base_url;
+
+    // Login as an admin user.
+    $this->drupalLogin($this->admin_user);
+
+    // Test with query string ?amp
+    $this->drupalGet('admin/config/content/amp');
+    $this->assertResponse(200);
+    $this->assertRaw('Query string (www.example.com/article?amp)');
+    $edit = ["amp_url_format" => 'query_string'];
+    $this->drupalPost(NULL, $edit, t('Save configuration'));
+
+    // Create a node to test the url detection.
+    $this->drupalGet('node/add/article');
+    $this->assertResponse(200);
+    $edit = [
+      "title" => 'AMP Page foo test',
+      "body[und][0][value]" => 'Foo',
+      "path[alias]" => 'foo',
+    ];
+    $this->drupalPost(NULL, $edit, t('Save'));
+
+    // Check link rel on full display.
+    $this->drupalGet('foo');
+    $this->assertResponse(200);
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/foo?amp"');
+
+    // Same check as above, using node/nid.
+    $this->drupalGet('node/1');
+    $this->assertResponse(200);
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/foo?amp"');
+
+    // Check AMP page with prefix path 'amp' should 404.
+    $this->drupalGet('amp/foo');
+    $this->assertResponse(404);
+
+    // Check AMP page with suffix path 'amp' should 404.
+    $this->drupalGet('foo/amp');
+    $this->assertResponse(404);
+
+    // Check AMP page with query string ?amp.
+    $this->drupalGet('foo', array('query' => array('amp' => NULL)));
+    $this->assertResponse(200);
+    $this->assertRaw('<html amp lang');
+    $this->assertRaw('link rel="canonical" href="' . $base_url . '/foo"');
+
+    // Check admin UI is not an amp page.
+    $this->drupalGet('node/1/edit', array('query' => array('amp' => NULL)));
+    $this->assertNoRaw('<html amp lang');
+  }
+
+  /**
+   * Test the url with prefix path 'amp'.
+   */
+  public function testAmpUrlFormatPrefix() {
+    global $base_url;
+
+    // Login as an admin user.
+    $this->drupalLogin($this->admin_user);
+
+    // Test with prefix path 'amp'
+    $this->drupalGet('admin/config/content/amp');
+    $this->assertResponse(200);
+    $this->assertRaw('Path prefix (www.example.com/amp/article)');
+    $edit = ['amp_url_format' => 'prefix'];
+    $this->drupalPost(NULL, $edit, t('Save configuration'));
+    menu_cache_clear_all();
+
+    // Create a node to test the url detection.
+    $this->drupalGet('node/add/article');
+    $this->assertResponse(200);
+    $edit = [
+      "title" => 'AMP Page foo test',
+      "body[und][0][value]" => 'Foo',
+      "path[alias]" => 'foo',
+    ];
+    $this->drupalPost(NULL, $edit, t('Save'));
+
+    // Check link rel on full display.
+    $this->drupalGet('foo');
+    $this->assertResponse(200);
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/amp/foo"');
+
+    // Same check as above, using node/nid.
+    $this->drupalGet('node/1');
+    $this->assertResponse(200);
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/amp/foo"');
+
+    // Check AMP page with prefix path 'amp' should work.
+    $this->drupalGet('amp/foo');
+    $this->assertResponse(200);
+    $this->assertRaw('<html amp lang');
+    $this->assertRaw('link rel="canonical" href="' . $base_url . '/foo"');
+
+    // Check AMP page with suffix path 'amp' should 404.
+    $this->drupalGet('foo/amp');
+    $this->assertResponse(404);
+
+    // Check AMP page with query string ?amp should show full display.
+    $this->drupalGet('foo', array('query' => array('amp' => NULL)));
+    $this->assertResponse(200);
+    $this->assertNoRaw('<html amp lang');
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/amp/foo"');
+
+    // This should show full display.
+    $this->drupalGet('foo');
+    $this->assertResponse(200);
+    $this->assertNoRaw('<html amp lang');
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/amp/foo"');
+  }
+
+  /**
+   * Test the url with suffix path 'amp'.
+   */
+  public function testAmpUrlFormatSuffix() {
+    global $base_url;
+
+    // Login as an admin user.
+    $this->drupalLogin($this->admin_user);
+
+    // Test with suffix path 'amp'
+    $this->drupalGet('admin/config/content/amp');
+    $this->assertResponse(200);
+    $this->assertRaw('Path suffix (www.example.com/article/amp)');
+    $edit = ['amp_url_format' => 'suffix'];
+    $this->drupalPost(NULL, $edit, t('Save configuration'));
+    menu_cache_clear_all();
+
+    // Create a node to test the url detection.
+    $this->drupalGet('node/add/article');
+    $this->assertResponse(200);
+    $edit = [
+      "title" => 'AMP Page foo test',
+      "body[und][0][value]" => 'Foo',
+      "path[alias]" => 'foo',
+    ];
+    $this->drupalPost(NULL, $edit, t('Save'));
+
+    // Check link rel on full display.
+    $this->drupalGet('foo');
+    $this->assertResponse(200);
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/foo/amp"');
+
+    // Same check as above, using node/nid.
+    $this->drupalGet('node/1');
+    $this->assertResponse(200);
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/foo/amp"');
+
+    // Check AMP page with prefix path 'amp' should 404.
+    $this->drupalGet('amp/foo');
+    $this->assertResponse(404);
+
+    // Check AMP page with suffix path 'amp' should work.
+    $this->drupalGet('foo/amp');
+    $this->assertResponse(200);
+    $this->assertRaw('<html amp lang');
+    $this->assertRaw('link rel="canonical" href="' . $base_url . '/foo"');
+
+    // Check AMP page with query string ?amp should show full display.
+    $this->drupalGet('foo', array('query' => array('amp' => NULL)));
+    $this->assertResponse(200);
+    $this->assertNoRaw('<html amp lang');
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/foo/amp"');
+
+    // This should show full display.
+    $this->drupalGet('foo');
+    $this->assertResponse(200);
+    $this->assertNoRaw('<html amp lang');
+    $this->assertRaw('link rel="amphtml" href="' . $base_url . '/foo/amp"');
+  }
+
+}
