一个web端在线运行代码的php小项目的逐步实现

一个web端在线运行代码的php小项目的逐步实现

这个网站目前为止用的代码演示功能是借用了 https://tool.lu/coderunner/ 的在线运行代码工具,在此致谢。

前几天这个工具突然失效了,我就在想能不能自己模仿着做一个类似的出来,简单分析了一下就想挑战一下自己,然后就开始动手了,做的过程中查阅了很多网络资料,现整理如下:

技术需求分析:前端为一个实用的代码编辑器,通过ajax请求将写好的代码提交给服务器,服务器编译运行后把输出结果送回客户端显示。

其中使用的代码编辑器:CodeMirror,现在类似的工具使用的应该都是这款功能强大,可以自定样式的代码编辑器,官网: https://codemirror.net/

1. CodeMirror搭建前端

先从官网下载下来CodeMirror的压缩包,解压之后得到下图目录

要在html中创建一个CodeMirror编辑器,必须添加的css和js文件是

<link href=”./codemirror-5.48.2/lib/codemirror.css” rel=”stylesheet”/>

<script src=”./codemirror-5.48.2/lib/codemirror.js”></script>

(5.48.2为版本号,因人而异)

然后需要添加需要编辑的语言相关的js文件,可以在mode目录下找到,这里我用了两个文件:

实现JAVA和C++代码高亮(这个文件可以实现C,C++,JAVA,C#等语言):

<script src=”./codemirror-5.48.2/mode/clike/clike.js”></script>

实现python的代码高亮:

<script src=”./codemirror-5.48.2/mode/python/python.js”></script>

需要更改编辑器主题样式的可以在theme目录下找到对应的主题css文件添加进去,我觉得默认主题就很好看了就没用其他主题。

为了实现括号匹配和代码折叠功能,还要添加的文件有:

<link rel=”stylesheet” href=”./codemirror-5.48.2/addon/fold/foldgutter.css”/> 

<script src=”./codemirror-5.48.2/addon/fold/foldcode.js”></script>
<script src=”./codemirror-5.48.2/addon/fold/foldgutter.js”></script>
<script src=”./codemirror-5.48.2/addon/fold/brace-fold.js”></script>
<script src=”./codemirror-5.48.2/addon/fold/comment-fold.js”></script>

创建编辑器的过程:

在html中使用一个textarea占位,配置好id:

<textarea  id=”code” name=”code”></textarea>

通过对应的js代码创建编辑器:

var editor = CodeMirror.fromTextArea(document.getElementById("code"), {
	mode: "text/x-java", //实现Java代码高亮
	//mode: "text/x-c++src", //实现C++代码高亮
	//mode: "text/x-python", //实现Python代码高亮
  	indentUnit:4,//以四个空格的长度缩进
	indentWithTabs: true,//以tab代替空格缩进
	lineNumbers: true,	//显示行号
	lineWrapping: true,	
	foldGutter: true, //代码折叠
	gutters: ["CodeMirror-linenumbers", "CodeMirror-foldgutter"],
	matchBrackets: true	//括号匹配      
});

这里需要什么语言高亮需要在官网找到对应语言的 MIME types ,写在mode参数中

其他相关js函数:

编辑器的大小通过editor.setSize(width, height)方法设置

获取编辑器内的代码:editor.getValue()

设置编辑器内的代码: editor.setValue()

最终搭配上bootstrap样式做出来的效果是这样的:

2. js实现ajax

我这里使用了原生js实现ajax:将编程语言和代码内容以表单数据的形式POST到后端等待返回结果

关键代码:

创建代理对象

var xhr = new XMLHttpRequest();

设置请求头

xhr.setRequestHeader(‘Content-Type’,’application/x-www-form-urlencoded’)

发出数据

xhr.send(‘lang=java&codesrc=’ + codesrc)

接收数据

xhr.onreadystatechange = function(){
if(this.readyState !== 4) return; 
/*
 处理数据 
*/ 
}

注: 由于代码中可能出现’+’或’&’符号,其在post的请求中经过urlencode会分别被解析为空格和参数连接符,需先将代码源码用js的encodeURIComponent()函数编码,传递到php后端后再用rawurldecode()函数进行解码操作。

3. php实现后端

php的任务是在服务器上运行代码,用到了exec函数

具体参阅 【php】php使用exec总结

做的时候遇到了个问题:php在调用exec执行gcc命令时,会出现各种毛病,例如ld链接器找不到,后来发现原因是php不会使用系统设置的环境变量,在php文件开头添加这样一句话就能解决问题:

putenv(“PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin”);//设置环境变量

4+
Rhett Peng

软件工程大三在读学生,用个人网站记录学习动态

说点什么

avatar