DinkToPdf icon indicating copy to clipboard operation
DinkToPdf copied to clipboard

Can I access DinkToPdf in .Net Framework 4.6.1?

Open lad-rachana opened this issue 6 years ago • 10 comments

Hello @rdvojmoc , Can I access DinkToPdf in .Net Framework 4.6.1? If yes, then what are the dependencies for that? Thank you!

lad-rachana avatar Jul 02 '18 05:07 lad-rachana

No, it's only available for NET Core. Please check TuesPechkin which should support NET Framework 4.6.1 and have very similar functionality as DinkToPdf.

rdvojmoc avatar Jul 02 '18 07:07 rdvojmoc

@rdvojmoc - Getting "Cannot marshal 'parameter #2': Invalid managed/unmanaged type combination (String parameters and return types must be paired with LPStr, LPWStr, LPTStr, BStr, TBStr, VBByRefStr, or AnsiBStr)." exception when using this library.

patel-sagar avatar Jul 02 '18 09:07 patel-sagar

You can use netstandard1.6 libs from .Net Framework 4.6.1. https://docs.microsoft.com/en-us/dotnet/standard/net-standard

VahidN avatar Jul 02 '18 10:07 VahidN

@VahidN @rdvojmoc - Getting "Cannot marshal 'parameter #2': Invalid managed/unmanaged type combination (String parameters and return types must be paired with LPStr, LPWStr, LPTStr, BStr, TBStr, VBByRefStr, or AnsiBStr)." exception when using this library.

Any idea what caused this issue?

patel-sagar avatar Jul 02 '18 10:07 patel-sagar

@patel-sagar Provide some context in which this exception is thrown (OS, NET Core version, where it's deployed, etc...)

rdvojmoc avatar Jul 05 '18 16:07 rdvojmoc

I also had to use it on net461. I downloaded the source and change TargetFramework in DinkToPdf.csproj like this <TargetFramework>net461</TargetFramework>.

Compile it, add reference and it works well.

sergei66666 avatar Nov 19 '18 14:11 sergei66666

@sergei66666 Are you shure this is the case? It really works for you inside a framework 4.6.1 app? I have tryed <TargetFramework>net461</TargetFramework> and it does not work for me. I simply cannot get this api to work in a framework app aldo it should work, as it is a .net standard api whoose raison d'etre is to work in .net core and in .net framework environment. i get this error in DinkToPdf.PdfTools public void Load() method line 27: if (WkHtmlToXBindings.wkhtmltopdf_init(0) == 1) :

Managed Debugging Assistant 'PInvokeStackImbalance' : 'A call to PInvoke function 'DinkToPdf!DinkToPdf.WkHtmlToXBindings::wkhtmltopdf_init' has unbalanced the stack. This is likely because the managed PInvoke signature does not match the unmanaged target signature. Check that the calling

@sergei66666 can you please send me a list / image of your framework project references. This would be most helpful. Also a link to wkhtmltox/libwkhtmltox.dll you are using and if your machine runs on a 32 bit os. Maybe also a project properties window image... anything you might think would help.

fashrista avatar Sep 18 '19 12:09 fashrista

@fashrista I used net461 from Nov 2018 to March 2019 in all my projects inside solution. It worked on my dev machine (windows 10) and in azure service. I used wkhtmltox-0.12.5. If i remember correctly it was x64 libs.

I assume that there can be two problems:

  1. wrong version of wkhtmltox
  2. wrong architecture.

I download lib from x32 and x64

sergei66666 avatar Sep 18 '19 14:09 sergei66666

What I did: I have downloaded the x64 wkhtmltox.dll from the link @sergei66666 provided, renamed it to "libwkhtmltox.dll" and stored it to the right path. I have downloaded the DinkToPdf project from github. I have changed the <TargetFramework>netcore1.1</TargetFramework> to <TargetFramework>net461</TargetFramework>. Rebuilt the entire solution. I have added a net framework 4.6.1 project to this solution and changed the properties so it will only run on 64 bit. I have changed the way the native dll is loaded since framework solutions do not include System.Runtime.Loader:

`class Program
    {
        static void Main(string[] args)
        {
            var architectureFolder = (IntPtr.Size == 8) ? "64 bit" : "32 bit";
            var wkHtmlToPdfPath = Path.Combine(AppContext.BaseDirectory, $"wkhtmltox\\v0.12.4\\{architectureFolder}\\libwkhtmltox.dll");
         
            IntPtr pDll = NativeMethods.LoadLibrary(wkHtmlToPdfPath);
            if (pDll == IntPtr.Zero)
            {
                throw new FileNotFoundException("-- Cannot load libwkhtmltox == a dll used for html to pdf convertion --");
            }


            var converter = new BasicConverter(new PdfTools());

            converter.PhaseChanged += Converter_PhaseChanged;
            converter.ProgressChanged += Converter_ProgressChanged;
            converter.Finished += Converter_Finished;
            converter.Warning += Converter_Warning;
            converter.Error += Converter_Error;

            var doc = new HtmlToPdfDocument()
            {
                GlobalSettings = {
                    ColorMode = ColorMode.Color,
                    Orientation = Orientation.Landscape,
                    PaperSize = PaperKind.A4,
                },
                Objects = {
                    new ObjectSettings() {
                        PagesCount = true,
                        HtmlContent = @"Lorem ipsum dolor sit amet, consectetur adipiscing elit. In consectetur mauris eget ultrices iaculis....",
                        WebSettings = { DefaultEncoding = "utf-8" },
                        HeaderSettings = { FontSize = 9, Right = "Page [page] of [toPage]", Line = true },
                        FooterSettings = { FontSize = 9, Right = "Page [page] of [toPage]" }
                    }
                }
            };
            byte[] pdf = converter.Convert(doc);

            if (!Directory.Exists("Files"))
            {
                Directory.CreateDirectory("Files");
            }
            using (FileStream stream = new FileStream(@"Files\" + DateTime.UtcNow.Ticks.ToString() + ".pdf", FileMode.Create))
            {
                stream.Write(pdf, 0, pdf.Length);
            }
            Console.ReadKey();
        }
        #region events
        private static void Converter_Error(object sender, DinkToPdf.EventDefinitions.ErrorArgs e)
        {
            Console.WriteLine("[ERROR] {0}", e.Message);
        }

        private static void Converter_Warning(object sender, DinkToPdf.EventDefinitions.WarningArgs e)
        {
            Console.WriteLine("[WARN] {0}", e.Message);
        }

        private static void Converter_Finished(object sender, DinkToPdf.EventDefinitions.FinishedArgs e)
        {
            Console.WriteLine("Conversion {0} ", e.Success ? "successful" : "unsucessful");
        }

        private static void Converter_ProgressChanged(object sender, DinkToPdf.EventDefinitions.ProgressChangedArgs e)
        {
            Console.WriteLine("Progress changed {0}", e.Description);
        }

        private static void Converter_PhaseChanged(object sender, DinkToPdf.EventDefinitions.PhaseChangedArgs e)
        {
            Console.WriteLine("Phase changed {0} - {1}", e.CurrentPhase, e.Description);
        }
    }
    #endregion
    static class NativeMethods
    {
        [DllImport("kernel32.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern IntPtr LoadLibrary(string dllToLoad);

        [DllImport("kernel32.dll")]
        public static extern IntPtr GetProcAddress(IntPtr hModule, string procedureName);


        [DllImport("kernel32.dll")]
        public static extern bool FreeLibrary(IntPtr hModule);

        public static string GetLibraryPathname(string filename)
        {
            // If 64-bit process, load 64-bit DLL
            bool is64bit = true;

            string prefix = "Win32";

            if (is64bit)
            {
                prefix = "x64";
            }

            var lib1 = prefix + @"\" + filename;

            return lib1;
        }
    }`

What happened: When I run the framework project that references the DinkToPdf I get this error in DinkToPdf.BasicConverter method - CreateConverter(IDocument document), line - ApplyConfig(settings, document, true); :

System.IO.FileNotFoundException: 'Could not load file or assembly 'System.Reflection.TypeExtensions, Version=4.1.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a' or one of its dependencies. The system cannot find the file specified.'

System.Reflection.TypeExtensions v 4.3 is added as a nuget to DinkToPdf project and have tryed downgradeing it to 4.1 and upgradeing to a latest preview 4.6 but to no avail.

What I expected: I allways expect things to work right out of the box ;D Any sugestions??

fashrista avatar Sep 23 '19 10:09 fashrista

@fashrista If I know correctly github is not correct place for this discussion. But..

A long time ago I had 2 projects:

  1. Console net461
  2. DinkToPdf

1 had referense to 2. Inside 2 i put x64 version of libwkhtmltox.dll and set it property 'Copy to output Directory'='Copy if newer'. Remove all code which load library and start from var converter = new BasicConverter(new PdfTools());

p.s. I don't know how to load library at runtime on net461. I tried but without luck.

sergei66666 avatar Sep 23 '19 12:09 sergei66666