radimitrov / CSharpShellApp

77 stars 18 forks source link

Load an DLL #345

Closed PeterKaa1 closed 5 months ago

PeterKaa1 commented 7 months ago

Using some code like this one:

using System;
using System.Reflection;

class Program
{
    static void Main()
    {
        string dllPath = "FileOperations.dll";
        Assembly assembly = Assembly.LoadFrom(dllPath);
        string className = "YourNamespace.YourClass";
        string methodName = "YourMethod";
        object classInstance = assembly.CreateInstance(className);

        if (classInstance != null)
        {
            MethodInfo method = classInstance.GetType().GetMethod(methodName);

            if (method != null)
            {
                object result = method.Invoke(classInstance, null);
                Console.WriteLine("Result: " + result);
            }
            else
            {
                Console.WriteLine("Method not found.");
            }
        }
        else
        {
            Console.WriteLine("Class not found.");
        }
    }
}

I can load up an DLL when im running the program in the IDE (Class gets not found because the code is unfinished) but when i export the APK i get this error:

System.IO.FileNotFoundException: Could not load file or assembly '/data/data/com.peterkaa.operations/files/FileOperations.dll' or one of its dependencies.
    at Program.Main() in Program.cs:9 [9:9-9:47]

Where do i put the DLL so it can get stored somewhere in the APK and get loaded when i run the APK? I know that i can add it as an external reference which puts it in the "assemblies" folder in the APK.

FileOperations.dll contains those scripts:

CreateFile.cs:

using System;

namespace FileOperations
{
    public class CreateFile
    {
        public static void Main()
        {
            Console.WriteLine("Testing.");
        }
    }
}

DeleteFile.cs:

using System;

namespace FileOperations
{
    public class DeleteFile
    {
        public static void Main()
        {
            Console.WriteLine("Testing.");
        }
    }
}

EditFile.cs:

using System;

namespace FileOperations
{
    public class EditFile
    {
        public static void Main()
        {
            Console.WriteLine("Testing.");
        }
    }
}

MoveFile.cs:

using System;

namespace FileOperations
{
    public class MoveFile
    {
        public static void Main()
        {
            Console.WriteLine("Testing.");
        }
    }
}

RenameFile.cs:

using System;

namespace FileOperations
{
    public class RenameFile
    {
        public static void Main()
        {
            Console.WriteLine("Testing.");
        }
    }
}
radimitrov commented 7 months ago

If you want to use reflection here instead of directly using the assembly via code have 3 options.

  1. If the DLL is referenced then you should be able to load it in the APK with var assem = Assembly.Load("FileOperations").
  2. The assembly can't be accessed like a file in the "assemblies directory" so if you want a stream you need to Microsoft.Maui.ApplicationModel.Platform.CurrentActivity.Assets.OpenNonAssetFd("assemblies/FileOperations.dll").CreateInputStream();.
  3. Or pack as a resource or asset and use CSharpShellCore.Utils.GetAsset() to get a stream. Then it would be simplest to do something like this: var ms = new MemoryStream(); assetStream.CopyTo(ms); ms.Position=0; var assem = Assembly.Load(ms.ToArray());