问题
I need to make a simple vb.net program that runs a piece of code entered by the user (also in vb.net). But I need my program to compile and run it.
Anyone have an idea on how to do this?
回答1:
I actually wrote a blog post (link below) about this several years ago. The below example is from 2010, and there may be better methods to solve this problem today. More explanation can be found in the code comments.
Essentially:
- Read the code from the file.
- Create an instance of a VB.NET CodeProvider
- Create compiler parameters and pass them to the compiler
- Compile the code
- Check for errors
- Create an instance of the class containing the code
- Create arguments to pass to our compiled code
- Execute the code and see results
An example of this being utilized to execute code in a text file and displaying a result in a TextBox is below, but could easily be used to parse code from a Textbox. (more info at vbCity Blog):
Includes:
Imports System.IO
Imports System.Reflection
Imports System.CodeDom
Imports System.CodeDom.Compiler
Imports Microsoft.VisualBasic
Code:
' Read code from file
Dim input = My.Computer.FileSystem.ReadAllText("Code.txt")
' Create "code" literal to pass to the compiler.
'
' Notice the <% = input % > where the code read from the text file (Code.txt)
' is inserted into the code fragment.
Dim code = <code>
Imports System
Imports System.Windows.Forms
Public Class TempClass
Public Sub UpdateText(ByVal txtOutput As TextBox)
<%= input %>
End Sub
End Class
</code>
' Create the VB.NET Code Provider.
Dim vbProv = New VBCodeProvider()
' Create parameters to pass to the compiler.
Dim vbParams = New CompilerParameters()
' Add referenced assemblies.
vbParams.ReferencedAssemblies.Add("mscorlib.dll")
vbParams.ReferencedAssemblies.Add("System.dll")
vbParams.ReferencedAssemblies.Add("System.Windows.Forms.dll")
vbParams.GenerateExecutable = False
' Ensure we generate an assembly in memory and not as a physical file.
vbParams.GenerateInMemory = True
' Compile the code and get the compiler results (contains errors, etc.)
Dim compResults = vbProv.CompileAssemblyFromSource(vbParams, code.Value)
' Check for compile errors
If compResults.Errors.Count > 0 Then
' Show each error.
For Each er In compResults.Errors
MessageBox.Show(er.ToString())
Next
Else
' Create instance of the temporary compiled class.
Dim obj As Object = compResults.CompiledAssembly.CreateInstance("TempClass")
' An array of object that represent the arguments to be passed to our method (UpdateText).
Dim args() As Object = {Me.txtOutput}
' Execute the method by passing the method name and arguments.
Dim t As Type = obj.GetType().InvokeMember("UpdateText", BindingFlags.InvokeMethod, Nothing, obj, args)
End If
来源:https://stackoverflow.com/questions/22264142/how-to-compile-code-entered-by-the-user