当前位置: 首页 > news >正文

用C语言做一个web站,富文本写入与展示,用户登录,文本目录划分

目录

      • 1. 基础准备
        • 必备工具:
      • 2. 目录结构
      • 3. 用户登录(使用简单的文件系统管理)
      • 4. 富文本编辑器和展示
      • 5. 样式文件
      • 6. 配置 Web 服务器
      • 7. 运行和测试

构建一个简单的 Web 站点实现富文本写入和展示、用户登录以及文本目录划分需要结合多个技术,包括 C 语言的 CGI(Common Gateway Interface)、HTML、JavaScript 和 CSS 以及一个简单的文件系统管理。下面是一个基本的实现步骤和示例代码。

1. 基础准备

必备工具:
  • 一个 Web 服务器(例如 Apache 或 Nginx)支持 CGI。
  • HTML、CSS 和 JavaScript 基础知识。
  • C 语言编译器(例如 gcc)。

2. 目录结构

/var/www/cgi-bin/      # 放置 CGI 脚本
/var/www/html/         # 放置 HTML 文件
/var/www/html/css/     # 放置 CSS 文件
/var/www/html/js/      # 放置 JavaScript 文件

3. 用户登录(使用简单的文件系统管理)

login.html(放在 /var/www/html/ 中):

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>User Login</title><link rel="stylesheet" href="css/style.css">
</head>
<body><form action="/cgi-bin/login.cgi" method="post"><label for="username">Username:</label><input type="text" id="username" name="username" required><label for="password">Password:</label><input type="password" id="password" name="password" required><button type="submit">Login</button></form>
</body>
</html>

login.cgi(放在 /var/www/cgi-bin/ 中):

#include <stdio.h>
#include <stdlib.h>
#include <string.h>void get_post_data(char *data) {char *lenstr;long len;lenstr = getenv("CONTENT_LENGTH");if(lenstr == NULL || sscanf(lenstr,"%ld",&len)!=1 || len>1024) {printf("Content-type:text/html\n\n");printf("<html><body>Invalid POST data</body></html>");exit(1);}fgets(data, len+1, stdin);
}int main() {char data[1024];char username[100], password[100];get_post_data(data);sscanf(data, "username=%99[^&]&password=%99s", username, password);// 简单的用户名密码验证 (应替换为更安全的方法)if(strcmp(username, "admin") == 0 && strcmp(password, "password") == 0) {printf("Content-type:text/html\n\n");printf("<html><body>Login successful!<br><a href=\"editor.html\">Go to Editor</a></body></html>");} else {printf("Content-type:text/html\n\n");printf("<html><body>Invalid credentials. <a href=\"/login.html\">Try again</a></body></html>");}return 0;
}

4. 富文本编辑器和展示

editor.html(放在 /var/www/html/ 中):

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Rich Text Editor</title><link rel="stylesheet" href="css/style.css"><script src="js/editor.js"></script>
</head>
<body><form action="/cgi-bin/save_text.cgi" method="post"><textarea id="editor" name="editor" rows="10" cols="80"></textarea><button type="submit">Save</button></form><div><h2>Text Directory</h2><ul id="directory"></ul></div>
</body>
</html>

editor.js(放在 /var/www/html/js/ 中):

document.addEventListener("DOMContentLoaded", function() {const directory = document.getElementById('directory');// Fetch directory contentsfetch('/cgi-bin/list_texts.cgi').then(response => response.json()).then(data => {data.forEach(file => {let li = document.createElement('li');let a = document.createElement('a');a.href = `/cgi-bin/display_text.cgi?file=${file}`;a.innerText = file;li.appendChild(a);directory.appendChild(li);});});
});

save_text.cgi(放在 /var/www/cgi-bin/ 中):

#include <stdio.h>
#include <stdlib.h>
#include <string.h>void get_post_data(char *data) {char *lenstr;long len;lenstr = getenv("CONTENT_LENGTH");if(lenstr == NULL || sscanf(lenstr,"%ld",&len)!=1 || len>8192) {printf("Content-type:text/html\n\n");printf("<html><body>Invalid POST data</body></html>");exit(1);}fgets(data, len+1, stdin);
}void save_to_file(const char *filename, const char *data) {FILE *file = fopen(filename, "w");if(file == NULL) {printf("Content-type:text/html\n\n");printf("<html><body>Could not save file.</body></html>");exit(1);}fprintf(file, "%s", data);fclose(file);
}int main() {char data[8192];get_post_data(data);// Saving the data to a file (simple naming, should be more secure)save_to_file("/var/www/texts/saved_text.html", data);printf("Content-type:text/html\n\n");printf("<html><body>Text saved! <a href=\"editor.html\">Back to Editor</a></body></html>");return 0;
}

list_texts.cgi(放在 /var/www/cgi-bin/ 中):

#include <stdio.h>
#include <stdlib.h>
#include <dirent.h>
#include <string.h>int main() {DIR *d;struct dirent *dir;char result[8192] = "[";d = opendir("/var/www/texts/");if(d) {while((dir = readdir(d)) != NULL) {if(dir->d_type == DT_REG) {strcat(result, "\"");strcat(result, dir->d_name);strcat(result, "\",");}}closedir(d);if(result[strlen(result) - 1] == ',') {result[strlen(result) - 1] = '\0';}}strcat(result, "]");printf("Content-type: application/json\n\n");printf("%s", result);return 0;
}

display_text.cgi(放在 /var/www/cgi-bin/ 中):

#include <stdio.h>
#include <stdlib.h>
#include <string.h>void display_file(const char *filename) {FILE *file = fopen(filename, "r");if(file == NULL) {printf("Content-type:text/html\n\n");printf("<html><body>Could not open file.</body></html>");exit(1);}printf("Content-type:text/html\n\n");printf("<html><body>");char ch;while((ch = fgetc(file)) != EOF) {putchar(ch);}printf("</body></html>");fclose(file);
}int main(int argc, char *argv[]) {char *query_string = getenv("QUERY_STRING");char filename[256];if(query_string == NULL || sscanf(query_string, "file=%255s", filename) != 1) {printf("Content-type:text/html\n\n");printf("<html><body>Invalid file request.</body></html>");exit(1);}char filepath[512];snprintf(filepath, sizeof(filepath), "/var/www/texts/%s", filename);display_file(filepath);return 0;
}

5. 样式文件

style.css(放在 /var/www/html/css/ 中):

body {font-family: Arial, sans-serif;margin: 20px;
}form {margin-bottom: 20px;
}textarea {width: 100%;height: 200px;
}button {padding: 10px 20px;background-color: #4CAF50;color: white;border: none;cursor: pointer;
}button:hover {background-color: #45a049;
}

6. 配置 Web 服务器

确保你的 Web 服务器配置正确,并支持 CGI 脚本。例如,如果你使用 Apache,确保 httpd.conf 中有如下配置:

ScriptAlias /cgi-bin/ "/var/www/cgi-bin/"
<Directory "/var/www/cgi-bin">AllowOverride NoneOptions +ExecCGIAddHandler cgi-script .cgi .pl .pyRequire all granted
</Directory>

7. 运行和测试

  • 将所有文件放在对应的目录中。
  • 访问 http://yourserver/login.html 进行用户登录。
  • 成功登录后,访问富文本编辑器进行内容输入和保存。
  • 确保你有 `/var/www

/texts/` 目录用来保存文本文件,并具有写权限。

这只是一个基础的示例,实际应用中需要考虑更多安全性和功能性方面的细节。

相关文章:

  • 计算神经网络中梯度的核心机制 - 反向传播(backpropagation)算法(1)
  • Python错误集锦:faker模块生成xml文件时提示:`xml` requires the `xmltodict` Python library
  • 通过rediss实现用户菜单智能推荐
  • 基于YOLOv9+pyside的安检仪x光危险物物品检测(有ui)
  • 慧哥Saas充电桩开源平台 V2.5.5
  • SQL经典面试题
  • PHP pwn 学习 (1)
  • 开源模型应用落地-FastAPI-助力模型交互-WebSocket篇(六)
  • 用MySQL+node+vue做一个学生信息管理系统(一):配置项目
  • 【 木兰宽松许可证】
  • win10下Python的安装和卸载
  • 【Python】.py和.pyc文件的区别
  • 【深度学习】注意力机制
  • Unity | Shader基础知识(第十七集:学习Stencil并做出透视效果)
  • 华为SRv6 policy EVPN配置案例
  • IE9 : DOM Exception: INVALID_CHARACTER_ERR (5)
  • 【vuex入门系列02】mutation接收单个参数和多个参数
  • AngularJS指令开发(1)——参数详解
  • C# 免费离线人脸识别 2.0 Demo
  • ECMAScript入门(七)--Module语法
  • es6
  • Git学习与使用心得(1)—— 初始化
  • HTTP那些事
  • javascript从右向左截取指定位数字符的3种方法
  • JS+CSS实现数字滚动
  • Vue2.0 实现互斥
  • 创建一个Struts2项目maven 方式
  • 对话:中国为什么有前途/ 写给中国的经济学
  • 容器服务kubernetes弹性伸缩高级用法
  • 如何借助 NoSQL 提高 JPA 应用性能
  • 设计模式 开闭原则
  • 使用Tinker来调试Laravel应用程序的数据以及使用Tinker一些总结
  • 学习笔记DL002:AI、机器学习、表示学习、深度学习,第一次大衰退
  • 一个SAP顾问在美国的这些年
  •  一套莫尔斯电报听写、翻译系统
  • 译米田引理
  • 机器人开始自主学习,是人类福祉,还是定时炸弹? ...
  • # 深度解析 Socket 与 WebSocket:原理、区别与应用
  • ### RabbitMQ五种工作模式:
  • #Js篇:单线程模式同步任务异步任务任务队列事件循环setTimeout() setInterval()
  • #pragma multi_compile #pragma shader_feature
  • #考研#计算机文化知识1(局域网及网络互联)
  • #我与Java虚拟机的故事#连载05:Java虚拟机的修炼之道
  • $.ajax()参数及用法
  • (23)Linux的软硬连接
  • (html5)在移动端input输入搜索项后 输入法下面为什么不想百度那样出现前往? 而我的出现的是换行...
  • (笔记)M1使用hombrew安装qemu
  • (二)c52学习之旅-简单了解单片机
  • (二)斐波那契Fabonacci函数
  • (附表设计)不是我吹!超级全面的权限系统设计方案面世了
  • (附源码)计算机毕业设计SSM基于java的云顶博客系统
  • (七)MySQL是如何将LRU链表的使用性能优化到极致的?
  • (学习日记)2024.02.29:UCOSIII第二节
  • (原創) 未来三学期想要修的课 (日記)
  • (正则)提取页面里的img标签