Search code examples
c#winformswebview2

Use indexedDB and local storage in webview2 when navigating to string


Im new to webview2 and is currently making a singlefile winforms app and my understanding so far is that i have to use Stream stream = assembly.GetManifestResourceStream(); to read embedded resources to do that.

The .net version is 6.0 and I have no other dependencies other than webview2. I have my webfiles in a folder in my solution which are embedded resources.

My problem is that when using that method I get the error 'IDBFactory': access to the Indexed Database API is denied in this context. when using indexedDB. I also get this error with localStorage Failed to read the 'localStorage' property from 'Window': Access is denied for this document..

I have set these flags in my environment: CoreWebView2EnvironmentOptions options = new CoreWebView2EnvironmentOptions("--allow-file-access-from-files --disable-web-security --allow-file-access"); I have no idea if they actually get applied but I don't see why they wouldn't be.

My UDF is in my temp folder which it can write to.

Is there someway to actually use indexedDb this way or should I do it another way?

(My first stackoverflow post so please tell me if I forgot to mention something or if there is something I should do better)


Solution

  • The way I solved it was by following the instructions from this post: https://stackoverflow.com/a/72105217/3943588 which I found thanks to David Risney.

    I did have to do it in a kinda round about way however.

    This was the code I ended up using:

        public async Task InitializeCoreWebView2Async(WebView2 webView, 
            webView.CoreWebView2.AddWebResourceRequestedFilter(filter,
                                                       CoreWebView2WebResourceContext.All);
            webView.CoreWebView2.WebResourceRequested += CoreWebView2_WebResourceRequested;
        }
    
        private void CoreWebView2_WebResourceRequested(object sender, CoreWebView2WebResourceRequestedEventArgs e)
        {
            var assembly = Assembly.GetExecutingAssembly();
            string resourcePath = assembly.GetManifestResourceNames().Where(r => r.StartsWith("{solution.namespace}") && r.EndsWith("index.html")).Single();
            using Stream stream = assembly.GetManifestResourceStream(resourcePath);
            using StreamReader reader = new StreamReader(stream);
    
            String streamAsText = string.Concat(reader.ReadToEnd()).Replace(Environment.NewLine, "");
    
            CoreWebView2WebResourceResponse response = webView.CoreWebView2.Environment.CreateWebResourceResponse(
                new MemoryStream(Encoding.UTF8.GetBytes(streamAsText)),
                200, "OK", "Content-Type: text/html; charset=utf-8");
            e.Response = response;
        }
    

    The reason for creating a stream to read the resource and then changing it to a string and then back again is because of the way that it uses the stream information.

    The stream information has a lot of newlines and linespaces which does so it doesn't send the whole stream. So I instead read the stream and then concatenate it and removes all newlines so I then can change it to a stream and send it.

    Just comment if you have any questions and I will try to respond asap.