硬汉嵌入式论坛

 找回密码
 立即注册
查看: 2184|回复: 5
收起左侧

[RL-TCPnet教程] 【RL-TCPnet网络教程】第46章 RL-TCPnet中CGI脚本使用方法

[复制链接]

740

主题

1326

回帖

3546

积分

管理员

春暖花开

Rank: 9Rank: 9Rank: 9

积分
3546
QQ
发表于 2018-1-9 15:31:09 | 显示全部楼层 |阅读模式
本帖最后由 席萌0209 于 2018-1-9 15:33 编辑

第46章      RL-TCPnet中CGI脚本使用方法

      本章节为大家讲解RL-TCPnet中CGI的实现方法,特别是具体的执行过程说明。关于这点非常有必要讲解下,否则后面学习了CGI也是云里雾里。
46.1 初学者重要提示
46.2 CGI实现动态HTML
46.3 Web网页的数据输入方法
46.4 CGI的POST数据输入方法
46.5 CGI的GET数据输入方法
46.6      总结



46.1  初学者重要提示
1、学习本章节前,务必优先学HTML表单,非常非常重要。已经整理在这个帖子中,由于有不是我们创作的内容,就不往教程里面整理了:http://bbs.armfly.com/read.php?tid=35826
2、CGI是HTTP和C代码通信的桥梁。基于此,客户端浏览器和Web服务器的互动才得以实现。
46.1.png

努力打造安富莱高质量微信公众号:点击扫描图片关注
回复

使用道具 举报

740

主题

1326

回帖

3546

积分

管理员

春暖花开

Rank: 9Rank: 9Rank: 9

积分
3546
QQ
 楼主| 发表于 2018-1-9 15:35:30 | 显示全部楼层
46.2  CGI实现动态HTML
      通过前面章节HTML的学习,我们了解到使用HTML仅仅可以制作一个静态网页,需要实现服务器和客户端的互动得需要CGI的加入。CGI属于一种脚本语言,加入到HTML中也比简单,仅需要下面五条指令,放在HTML语句前面即可:
46.2.png
加入了CGI脚本命令的文件,后缀名是.cgi。比如下面的HTML文件,我们希望它可以动态的显示信息,就可以为其添加CGI脚本命令:
  1. t <HTML><HEAD><TITLE> Hello World Example </TITLE></HEAD>

  2. t <H2 ALIGN=CENTER> Output a Greeting as Dynamic HTML </H2>

  3. c a <p> %s </p>

  4. t </BODY>

  5. t </HTML>

  6. .
复制代码

1、前两行以“t”脚本命令开始,表示该行是HTML语句,并将被发送到客户端浏览器。
2、第三行以“c”脚本命令开始,表示它是一个命令行。该行的其余部分将被传递到CGI接口函数cgi_func()的环境变量中。该环境变量称为env,将包含字符串“a <p>%s </ p>”。其中字符串开头的字母a是一个控制字符(控制字符不限制,可以是字母或者数字表示),而cgi_func()函数中必须包含解析这些字符的代码,然后格式化此行HTML代码的其余部分(所谓的格式化是指以HTML标准格式呈现)。
  1. U16 cgi_func (U8 *env, U8 *buf, U16 buflen, U32 *pcgi) {

  2. switch (env [0]) {

  3. case 'a':

  4. len = sprintf ((S8 *) buf, (const S8 *) &env [2], "Hello World");

  5. break;

  6. }



  7. return ((U16) len);

  8. }
复制代码

当用户使用浏览器加载网页时,switch语句的 case ‘a’子句将被执行。sprintf()语句就变成了
  1. len = sprintf ((S8 *) buf, <p>%s</p> , "Hello World");
复制代码

而buf就变成了:
  1. <p> Hello World </p>
复制代码

然后将其输出到浏览器。浏览器会显示HTML代码,如下所示:
  1. <HTML><HEAD><TITLE>Hello World</TITLE></HEAD>

  2. <BODY>

  3. <H2 ALIGN=CENTER>Output a Greeting as Dynamic HTML</H2>

  4. <p> Hello World </p>

  5. </BODY>
复制代码

浏览器的实际显示效果:
46.3.png
                              
用户可以应用CGI脚本到HTML文本的任何部分,以便实现HTML的动态显示。在上面举的例子中,只使用了一个用户定义控制字符,实际应用中可以使用多个控制字符来构建复杂的动态页面。

努力打造安富莱高质量微信公众号:点击扫描图片关注
回复

使用道具 举报

740

主题

1326

回帖

3546

积分

管理员

春暖花开

Rank: 9Rank: 9Rank: 9

积分
3546
QQ
 楼主| 发表于 2018-1-9 15:37:19 | 显示全部楼层
46.3  Web网页的数据输入方法
      接下来,我们来看看如何将数据从Web浏览器发送到服务器端的C应用程序中。CGI支持两种数据输入方法,GET和POST。两者都支持HTTP表单来输入数据,关于HTTP表单,看此贴即可,讲解比较详细http://bbs.armfly.com/read.php?tid=35826
1、GET方法
      如果表单提交是被动的(比如搜索引擎查询,输入查询不会更改网络上保存的任何数据),并且没有敏感信息,则应该使用GET方法。因为当用户使用 GET 时,表单数据在页面地址栏中是可见的:
  1. <font size="3">action_page.php?firstname=Mickey&lastname=Mouse</font>
复制代码

并且浏览器会设定容量限制,所以GET 适合少量数据的提交。

2、POST方法
      如果要使用输入数据进行更改,或者包含敏感信息(例如密码),则应使用POST方法,因为POST 安全性更好,且被提交的数据在页面地址栏中是不可见的。例如,将数据输入数据库来更改该数据库的状态,应使用POST方法。又比如将数据输入到一个小型的嵌入式Web服务器中,也应该使用POST方法。
      总的来说,GET方法适用于改变Web服务器中的环境变量,而POST方法用于用户和C应用程序代码之间传输数据。

努力打造安富莱高质量微信公众号:点击扫描图片关注
回复

使用道具 举报

740

主题

1326

回帖

3546

积分

管理员

春暖花开

Rank: 9Rank: 9Rank: 9

积分
3546
QQ
 楼主| 发表于 2018-1-9 15:39:29 | 显示全部楼层
46.4 CGI的POST数据输入方法
      下面通过一个实例讲解POST方式的数据输入,比如实现一个允许用户通过Web浏览器输入数据的功能,我们需要添加一个单元格和提交按钮到网页。基本代码如下:
  1. <html>

  2.   <head>

  3.     <title>Post example</title>

  4.   </head>

  5.   <body>

  6.     <form action="index.cgi" method="post" name="CGI">

  7.       <table>

  8.         <tr>

  9.           <td>

  10.             <input type="text" id="textbox1" size="16" value="" />

  11.           </td>

  12.           <td align="right">

  13.             <input type="submit" id="change" value="change" />

  14.           </td>

  15.         </tr>

  16.       </table>

  17.     </form>

  18.   </body>

  19. </html>
复制代码

反映到浏览器上的显示效果如下:
46.4.png
                              
用户查看此页面时,会看到单元格“textbox1”和提交按钮“change”。用户向单元格中填入数据后,按下按钮会触发POST数据输入方式,“textbox1”中的数据将传送到CGI接口函数。RL-TCPnet会调用HTTP_CGI.c文件中函数CGI_process_data()来处理。
  1. void cgi_process_data (U8 *dat, U16 len) {

  2. unsigned char text1 [16];

  3. var = (U8 *) alloc_mem (40);

  4. do {

  5. dat = http_get_var (dat, var, 40);

  6. if (var [0] != 0 ) {

  7. if (str_scomp (var, "textbox1") == __TRUE) {

  8. str_copy (text1, var+4); // extract user data

  9. process_Input (text1); // user function to process data

  10. }

  11. }

  12. }

  13. }
复制代码

      两个函数CGI_process_data()和CGI_process_var()分别用于POST和GET方式的数据处理。用户必须编写CGI_process_data()函数以便从textbox1单元格中获取数据。在函数CGI_process_data中申请一个名为var的缓冲区,然后通过调用函数http_get_var()复制字符串数据到缓冲区。这个字符串包含单元格的名称和已输入的任何数据。字符串格式如下:
  1. textbox1=<input text>
复制代码

      现在,用户需要做的就是添加代码来解析这个字符串并传递输入数据到C应用程序。基本的POST方法允许用户从任何HTML表单输入数据。但是用户点击了提交按钮后,表单将重新加载,会显示默认选项。比如设计的网页中使用了单选按钮和复选框之类的元素,重新加载后需要显示当前配置,而不能继续显示默认配置。为此,用户需要同时使用CGI动态HTML和CGI POST方法。当页面加载或刷新时,CGI_func()必须输出当前设置。如果输入新值,将继续由函数CGI_process_data()处理。
     对于一个简单的文本框,HTML需做如下修改:
  1. #

  2. # HTML with script commands

  3. #

  4. t <HTML>

  5. t <HEAD>

  6. t <TITLE>Post example</TITLE>

  7. t </HEAD>

  8. t <BODY>

  9. t <FORM ACTION="index.cgi" METHOD="POST" NAME="CGI">

  10. t <TABLE>

  11. t <TR>

  12. t <TD>

  13. c a <INPUT TYPE="TEXT" ID="textbox1" SIZE="16" VALUE="%"></TD>

  14. t <TD ALIGN="right">

  15. t <INPUT TYPE="SUBMIT" ID="change" VALUE="change"></TD>

  16. t </TR>

  17. t </TABLE>

  18. t </FORM>

  19. t </BODY>

  20. t </HTML>
复制代码

重新加载页面后,函数CGI_func()必须输出之前文本框中填写的内容。
  1. // From cgi_func() in HTTP_CGI.c

  2. case 'a':

  3. len = sprintf ((S8 *) buf, (const S8 *) &env [4], text1);

  4. break;
复制代码

通过上面这种方法,重新加载页面后,还将继续显示之前文本框中填写的内容。同样的方法可以应用于任何其他的HTML表单,如单选按钮、复选框和选择列表。

努力打造安富莱高质量微信公众号:点击扫描图片关注
回复

使用道具 举报

740

主题

1326

回帖

3546

积分

管理员

春暖花开

Rank: 9Rank: 9Rank: 9

积分
3546
QQ
 楼主| 发表于 2018-1-9 15:40:41 | 显示全部楼层
46.5 CGI的GET数据输入方法
      GET方式和POST方式的使用方法一样,HTML表单定义时,将POST方式改成GET方式即可:
  1. <FORM ACTION="network.cgi" METHOD="GET" NAME="CGI">
复制代码

当提交表单时,将触发函数CGI_process_var(),而POST触发的是函数CGI_process_data()。
进入函数后的处理方法是一样的:
  1. void cgi_process_var (U8 *qs) {

  2. U8 *var;

  3. var = (U8 *) alloc_mem (40);

  4. do {

  5. qs = http_get_var (qs, var, 40);

  6. if (var [0] != 0) {

  7. if (str_scomp (var, "query=" ) == __TRUE) {

  8. form_query_string (var+6);

  9. }

  10. ………

  11. }

  12. while (qs);

  13. free_mem ((OS_FRAME *) var);

  14. }

  15. }
复制代码


努力打造安富莱高质量微信公众号:点击扫描图片关注
回复

使用道具 举报

740

主题

1326

回帖

3546

积分

管理员

春暖花开

Rank: 9Rank: 9Rank: 9

积分
3546
QQ
 楼主| 发表于 2018-1-9 15:41:07 | 显示全部楼层
46.6 总结

      关于本章节的知识点还是比较重要的,需要初学者务必掌握,下一章节将进行实战。

努力打造安富莱高质量微信公众号:点击扫描图片关注
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|小黑屋|Archiver|手机版|硬汉嵌入式论坛

GMT+8, 2024-5-4 10:33 , Processed in 0.175062 second(s), 28 queries .

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2023, Tencent Cloud.

快速回复 返回顶部 返回列表