// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#import <WebKit/WebKit.h>

#include <memory>
#include <string>

#include "base/mac/foundation_util.h"
#import "base/mac/scoped_nsobject.h"
#include "base/memory/ptr_util.h"
#import "base/test/ios/wait_util.h"
#include "base/test/test_timeouts.h"
#include "ios/web/public/browser_state.h"
#import "ios/web/public/test/http_server.h"
#import "ios/web/public/test/js_test_util.h"
#import "ios/web/public/test/response_providers/string_response_provider.h"
#import "ios/web/public/web_view_creation_util.h"
#import "ios/web/test/web_int_test.h"
#import "net/base/mac/url_conversions.h"
#include "testing/gtest/include/gtest/gtest.h"
#import "testing/gtest_mac.h"

// A WKNavigationDelegate that is used to check if a WKWebView has finished
// a navigation. Used for testing purposes.
@interface TestNavigationDelegate : NSObject <WKNavigationDelegate>
// YES if a navigation has finished.
@property (nonatomic, assign) BOOL didFinishNavigation;
@end

@implementation TestNavigationDelegate

@synthesize didFinishNavigation = _didFinishNavigation;

- (void)webView:(WKWebView*)webView
    didFinishNavigation:(WKNavigation*)navigation {
  self.didFinishNavigation = YES;
}

@end

// A test fixture for testing that browsing data is partitioned between
// web views created with a non-OTR BrowserState and web views created with an
// OTR BrowserState.
class BrowserStateWebViewPartitionTest : public web::WebIntTest {
 protected:
  void SetUp() override {
    web::WebIntTest::SetUp();

    otr_browser_state_.SetOffTheRecord(true);

    web::test::HttpServer& server = web::test::HttpServer::GetSharedInstance();
    ASSERT_TRUE(server.IsRunning());

    auto provider =
        base::MakeUnique<web::StringResponseProvider>("Hello World");
    provider_ = provider.get();  // Keep a weak copy to allow unregistration.
    server.AddResponseProvider(std::move(provider));
  }

  void TearDown() override {
    web::test::HttpServer& server = web::test::HttpServer::GetSharedInstance();
    server.RemoveResponseProvider(provider_);
    provider_ = nullptr;

    web::WebIntTest::TearDown();
  }

  // Sets a persistent cookie with key, value on |web_view|.
  void SetCookie(NSString* key, NSString* value, WKWebView* web_view) {
    NSString* set_cookie = [NSString
        stringWithFormat:@"document.cookie='%@=%@;"
                         @"Expires=Tue, 05-May-9999 02:18:23 GMT; Path=/'",
                         key, value];
    web::ExecuteJavaScript(web_view, set_cookie);
  }

  // Returns a csv list of all cookies from |web_view|.
  NSString* GetCookies(WKWebView* web_view) {
    id result = web::ExecuteJavaScript(web_view, @"document.cookie");
    return base::mac::ObjCCastStrict<NSString>(result);
  }

  // Sets a localstorage key, value pair on |web_view|.
  void SetLocalStorageItem(NSString* key,
                           NSString* value,
                           WKWebView* web_view) {
    NSString* set_local_storage_item = [NSString
        stringWithFormat:@"localStorage.setItem('%@', '%@')", key, value];
    NSError* unused_error = nil;
    web::ExecuteJavaScript(web_view, set_local_storage_item, &unused_error);
  }

  // Returns the localstorage value associated with |key| from |web_view|.
  id GetLocalStorageItem(NSString* key, WKWebView* web_view) {
    NSString* get_local_storage_value =
        [NSString stringWithFormat:@"localStorage.getItem('%@');", key];
    return web::ExecuteJavaScript(web_view, get_local_storage_value);
  }

  // Loads a test web page (that contains a small string) in |web_view| and
  // waits until the web view has finished the navigation.
  void LoadTestWebPage(WKWebView* web_view) {
    DCHECK(web_view);

    base::scoped_nsobject<TestNavigationDelegate> navigation_delegate(
        [[TestNavigationDelegate alloc] init]);

    id old_navigation_delegate = web_view.navigationDelegate;
    web_view.navigationDelegate = navigation_delegate;

    web::test::HttpServer& server = web::test::HttpServer::GetSharedInstance();
    ASSERT_TRUE(server.IsRunning());

    NSURL* url = net::NSURLWithGURL(server.MakeUrl("http://whatever/"));
    [web_view loadRequest:[NSURLRequest requestWithURL:url]];
    base::test::ios::WaitUntilCondition(
        ^bool {
          return [navigation_delegate didFinishNavigation];
        },
        false, TestTimeouts::action_max_timeout());

    web_view.navigationDelegate = old_navigation_delegate;
  }

  // Returns the BrowserState that is used for testing.
  web::BrowserState* GetOtrBrowserState() { return &otr_browser_state_; }

 private:
  // The ResponseProvider used to load a simple web page.
  web::ResponseProvider* provider_;
  // The OTR browser state used in tests.
  web::TestBrowserState otr_browser_state_;
};

// Tests that cookies are partitioned between web views created with a
// non-OTR BrowserState and an OTR BrowserState.
// Flaky: crbug/684024
TEST_F(BrowserStateWebViewPartitionTest, DISABLED_Cookies) {
  WKWebView* web_view_1 = web::BuildWKWebView(CGRectZero, GetBrowserState());
  LoadTestWebPage(web_view_1);
  SetCookie(@"someCookieName1", @"someCookieValue1", web_view_1);
  EXPECT_NSEQ(@"someCookieName1=someCookieValue1", GetCookies(web_view_1));

  WKWebView* web_view_2 = web::BuildWKWebView(CGRectZero, GetOtrBrowserState());
  LoadTestWebPage(web_view_2);

  // Test that the cookie has not leaked over to |web_view_2|.
  EXPECT_NSEQ(@"", GetCookies(web_view_2));

  SetCookie(@"someCookieName2", @"someCookieValue2", web_view_2);
  EXPECT_NSEQ(@"someCookieName2=someCookieValue2", GetCookies(web_view_2));

  // Test that the cookie has not leaked over to |web_view_1|.
  NSString* cookies = GetCookies(web_view_1);
  EXPECT_FALSE([cookies containsString:@"someCookieName2"]);
}

// Tests that localStorage is partitioned between web views created with a
// non-OTR BrowserState and an OTR BrowserState.
TEST_F(BrowserStateWebViewPartitionTest, LocalStorage) {
  WKWebView* web_view_1 = web::BuildWKWebView(CGRectZero, GetBrowserState());
  LoadTestWebPage(web_view_1);
  SetLocalStorageItem(@"someKey1", @"someValue1", web_view_1);
  EXPECT_NSEQ(@"someValue1", GetLocalStorageItem(@"someKey1", web_view_1));

  WKWebView* web_view_2 = web::BuildWKWebView(CGRectZero, GetOtrBrowserState());
  LoadTestWebPage(web_view_2);

  // Test that LocalStorage has not leaked over to |web_view_2|.
  EXPECT_NSEQ([NSNull null], GetLocalStorageItem(@"someKey1", web_view_2));

  SetLocalStorageItem(@"someKey2", @"someValue2", web_view_2);
  // Due to platform limitation, it's not possible to actually set localStorage
  // item on an OTR BrowserState. Therefore, it's not possible to verify that a
  // localStorage item has been correctly set.
  // Look at
  // http://stackoverflow.com/questions/14555347/html5-localstorage-error-with-safari-quota-exceeded-err-dom-exception-22-an
  // for more details.
  // Test that LocalStorage has not leaked over to |web_view_1|.
  EXPECT_NSEQ([NSNull null], GetLocalStorageItem(@"someKey2", web_view_1));
}
