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

c++ 后台小练习--基于Vue的在线记事本

目录

效果

前端代码

后端代码


效果

前端使用vue3,后端使用Rester,

数据库采用cpp_redist实现的连接池。

前后端主要有获取事项,增加事项,删除事项几个简单的功能。完整的前端项目地址note_book地址

注意处理OPTIONS方法,重点注意allow这几个字段。

前端功能还可以继续增加,比如注册和登录。

为不同的用户存储各自的数据。

数据库连接池还可以进一步优化,考虑动态增加连接数量。

对于js, var self=this, 函数也是一个对象,也有this指针

对于log,程序关闭并不会将日志写完,只会强行kill后台线程。

因此在析构函数中join 后台日志写线程,并写完当前线程。

前端代码

<!--
 * @Author: hjhj111 2268716068@qq.com
 * @Date: 2022-08-30 12:15:37
 * @LastEditors: hjhj111 2268716068@qq.com
 * @LastEditTime: 2022-08-31 10:55:45
 * @FilePath: \note_book\src\components\HelloWorld.vue
 * @Description: 这是一个简单基于vue的在线备忘录,结合c++网络库Rester,内存数据库redis使用
-->
<template>
  <div>
    <h1>数据服务器地址: {{ address }}</h1>
    <ol style="list-style-type:none">
      <li v-for="note in notes" :key="note.text">
        <h2>{{note.text}}</h2>
        <button @click="deleteNote(note)">完成待办</button>
      </li>
    </ol>
    <!-- <form action={{this.adress}} method="post"> -->
      <input type="text"  id="form" placeholder="添加待办……">
      <input type="submit" value="确认添加" @click="addNote">
    <!-- </form> -->
  </div>  
</template>

<script>
//import { setgroups } from 'process';
import axios from 'axios'

export default {
  name: 'NoteBook',

  data(){
    return{
      notes:[
        {text:"hhhh"},
        {text:"jjjjj"}
      ],
      Address: this.address
    }    
  },

  props: {
    address:{default: "no url for data"},    
  },

  created(){
    this.getNotes()
    console.log(this.notes)  
  },
  
  methods:{   

    getNotes: function(){       
    console.log(this.address)        
    var self=this//修改父对象,函数也是对象
    axios.get(this.address).then(function(res){    
    console.log(res.data)
    self.notes=res.data
    console.log(self.notes)  
    }    
    ).catch((err)=>{
      console.log(err)      
    })    
    },

    addNote: function(){
      var self=this
      console.log(document.getElementById("form").value)
      axios({
        method:"Post",
        url:self.address,
        headers:{
          'Content-Type': 'text/plain'//application/json
        },
        data:{text:document.getElementById("form").value}
        //data:"{\"text\":\"更加发奋建安费\"}"
      }).then(function(res){
        if(res.status==201){
          //update
          self.getNotes();
          alert("添加完成");
        }
        else{
          alert("添加失败");
        }
      })
      
    },
    
    deleteNote: function(note){
      var self=this
      axios({
        method:"Delete",
        url:self.address,
        data:note
      }).then(function(res){
        if(res.status==201){
          //update
          self.getNotes()
          alert("删除成功")
        }
        else{
          alert("删除失败")
        }
      })
    }
  }
}
</script>

<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped>

</style>

后端代码

#include<iostream>
#include<string>
#include <signal.h>
#include"rester.h"

//#define MYTEST
shared_ptr<Rester> server_ptr;

void SigFunc(int sig)
{
    printf("sigfunc %d\n",sig);
    server_ptr->running_=false;
    signal(SIGINT,SIG_DFL);
}

int main(int argc, char *argv[])
{
#ifdef MYTEST
    fclose(stdout);
#endif
    Config config;
    config.Update();
    cout<<config;

    server_ptr=make_shared<Rester>(config);

    //close_log > 0 for close log
    if(!Log::get_instance()->init("log",0,8192,5000000,1000))
    {
        return 4;
    }
    printf("log inited\n");

    auto& connection_pool=ConnectionPool::GetInstance();//auto can not carry & itself

    Router note_book("/notes");//default router

    auto on_get= [&connection_pool](RequestPtr request_ptr,ResponsePtr response_ptr)
    {
        //auto client =ConnectToRedis();
        auto client=connection_pool.GetClient();
        ClientHelper client_helper(connection_pool,client);//for automatic return client
//        if(client== nullptr)
//        {
//            client =ConnectToRedis();
//        }
        cpp_redis::reply reply1;
//        client->get("notes_list", [&reply1](cpp_redis::reply& reply) {
//            reply1=reply;
//            std::cout << "get from redis: " << reply.as_string() << std::endl;
//        });
        auto notes_size=client->llen("notes_list");
        client->sync_commit();
        auto si=notes_size.get().as_integer()-1;
        std::cout<<si<<std::endl;
        client->lrange("notes_list",0,si,[&reply1](cpp_redis::reply& reply){
            if(reply.ok())
            {
                reply1=reply;
                std::cout << "get from redis: " << reply.is_array() << std::endl;
            }
            else
            {
                cout<<"error: "<<reply1.error()<<endl;
            }
        });
        client->sync_commit();

        string ret;
        auto arr=reply1.as_array();
        ret+="[";
        for(int i=0;i<arr.size();i++)
        {
            auto& re=arr[i];
            auto re_str=re.as_string();
            ret+=re_str;
            if(i==arr.size()-1)
            {
                continue;
            }
            ret+=",";
        }
        ret+="]";
        printf("list from redis: %s\n",ret.c_str());
        //client->shutdown();
        response_ptr->SetStatusCode(200);
        response_ptr->SetHeader("Content-Type", "application/json"); //application/x-zip-compressed
        response_ptr->SetHeader("Connection", "keep-alive");
        response_ptr->SetHeader("Access-Control-Allow-Origin","*");
        response_ptr->SetHeader("Allow","GET,POST,DELETE");
        response_ptr->PrintResponse();
//        char *buf2 = nullptr;
//        int length = ReadFileAll("notes.json", buf2);
//        response_ptr->SetData(buf2, length);
        int length=-1;
        length=ret.length();
        auto buf2=ret.c_str();
        response_ptr->SetData(buf2, length);

        response_ptr->CombineResponse();
        printf("read file all %s body_length: %d, response_length: %d \n", response_ptr->HeadersStr().c_str(),length,response_ptr->ResponseLen());
    };
    note_book.SetGet(on_get);

    auto on_post=[&connection_pool](RequestPtr request_ptr,ResponsePtr response_ptr)
    {
//        auto client =ConnectToRedis();
        auto client=connection_pool.GetClient();
        ClientHelper client_helper(connection_pool,client);//for automatic return client
        cpp_redis::reply reply1;
        cout<<"body: "<<(*request_ptr)["body"]<<(*request_ptr)["body"].size()<<endl;
        client->lpush("notes_list",vector<string>{(*request_ptr)["body"]},[response_ptr](cpp_redis::reply& reply){
            if(reply.ok())
            {
                response_ptr->SetStatusCode(201);
                response_ptr->SetHeader("Content-Type", "application/json"); //application/x-zip-compressed
                response_ptr->SetHeader("Access-Control-Allow-Origin","*");
                response_ptr->PrintResponse();
                response_ptr->CombineResponse();
            }
            else
            {
                response_ptr->SetStatusCode(406);
                response_ptr->SetHeader("Content-Type", "application/json"); //application/x-zip-compressed
                response_ptr->SetHeader("Access-Control-Allow-Origin","*");
                response_ptr->PrintResponse();
                response_ptr->CombineResponse();
            }
        });
        client->sync_commit();
        //printf("%s\n",reply1.as_string().c_str());
        //client->shutdown();
    };
    note_book.SetPost(on_post);

    auto on_options=[](RequestPtr request_ptr,ResponsePtr response_ptr)
    {
        response_ptr->SetStatusCode(200);
        response_ptr->SetHeader("Content-Type", "application/json"); //application/x-zip-compressed
        response_ptr->SetHeader("Access-Control-Allow-Origin","*");
        response_ptr->SetHeader("Access-Control-Allow-Headers","*");
        response_ptr->SetHeader("Access-Control-Allow-Methods","GET,POST,OPTIONS,DELETE");
        response_ptr->PrintResponse();
        response_ptr->CombineResponse();
    };
    note_book.SetOptions(on_options);

    auto on_delete=[&connection_pool](RequestPtr request_ptr,ResponsePtr response_ptr)
    {
//        auto client =ConnectToRedis();
        auto client=connection_pool.GetClient();
        ClientHelper client_helper(connection_pool,client);//for automatic return client
        cpp_redis::reply reply1;
        cout<<"body: "<<(*request_ptr)["body"]<<(*request_ptr)["body"].size()<<endl;
        client->lrem("notes_list",0,(*request_ptr)["body"],[response_ptr](cpp_redis::reply& reply){
            if(reply.ok())
            {
                cout<<"delete ok"<<endl;
                response_ptr->SetStatusCode(201);
                response_ptr->SetHeader("Content-Type", "application/json"); //application/x-zip-compressed
                response_ptr->SetHeader("Access-Control-Allow-Origin","*");
                response_ptr->PrintResponse();
                response_ptr->CombineResponse();
            }
            else
            {
                cout<<"delete error"<<endl;
                response_ptr->SetStatusCode(406);
                response_ptr->SetHeader("Content-Type", "application/json"); //application/x-zip-compressed
                response_ptr->SetHeader("Access-Control-Allow-Origin","*");
                response_ptr->PrintResponse();
                response_ptr->CombineResponse();
            }
        });
        client->sync_commit();
    };
    note_book.SetDelete(on_delete);

    auto on_close=[](ConnectionPtr conn)
    {
        struct in_addr tmp;
        tmp.s_addr=conn->ip_;
        auto str_ip=inet_ntoa(tmp);
        LOG_INFO("connection closed:%s: %d",str_ip,conn->port_);
        //cout<<"close loginfo"<<endl;
    };
    note_book.SetClose(on_close);


    server_ptr->AddWorker(note_book);


    signal(SIGINT,SigFunc);
    server_ptr->Init();
    return 0;
}

相关文章:

  • 超级简单快速上手Vue
  • 错误:ModuleNotFoundError: No module named ‘httplib‘
  • 力扣:22-括号生成
  • C# netcore 创建WebService(SoapCore)
  • ansible配置主机间免密登陆
  • 在项目中操作MySQL
  • 3倍通气的医用外科口罩,佩戴舒适过滤不打折
  • Linux文件及目录结构
  • lec formality inconclusive举例
  • 2022极端高温!人工智能如何预测森林火灾?| 万物AI
  • redis五大数据类型+redis6 新类型(详解+指令)
  • 【云原生 | 从零开始学Kubernetes】十七、Kubernetes核心技术Service
  • 传述最详细的干货,让简历面试不再成为你找工作的绊脚石
  • 【云原生丨Kubernetes系列⑥】集群的WEB UI管理⼯具:Dashboard 插件
  • 开学季征文|一个爱立Flag 的大冤种
  • 「前端」从UglifyJSPlugin强制开启css压缩探究webpack插件运行机制
  • 【comparator, comparable】小总结
  • 【跃迁之路】【444天】程序员高效学习方法论探索系列(实验阶段201-2018.04.25)...
  • 【跃迁之路】【585天】程序员高效学习方法论探索系列(实验阶段342-2018.09.13)...
  • Android路由框架AnnoRouter:使用Java接口来定义路由跳转
  • CentOS 7 修改主机名
  • Codepen 每日精选(2018-3-25)
  • passportjs 源码分析
  • php面试题 汇集2
  • React系列之 Redux 架构模式
  • Vue.js 移动端适配之 vw 解决方案
  • Windows Containers 大冒险: 容器网络
  • 精彩代码 vue.js
  • 买一台 iPhone X,还是创建一家未来的独角兽?
  • 前端之Sass/Scss实战笔记
  • 人脸识别最新开发经验demo
  • 我看到的前端
  • 应用生命周期终极 DevOps 工具包
  • 赢得Docker挑战最佳实践
  • raise 与 raise ... from 的区别
  • 国内唯一,阿里云入选全球区块链云服务报告,领先AWS、Google ...
  • 容器镜像
  • 组复制官方翻译九、Group Replication Technical Details
  • ###STL(标准模板库)
  • (C语言)strcpy与strcpy详解,与模拟实现
  • (solr系列:一)使用tomcat部署solr服务
  • (SpringBoot)第二章:Spring创建和使用
  • (二)Linux——Linux常用指令
  • (翻译)Quartz官方教程——第一课:Quartz入门
  • (附源码)php投票系统 毕业设计 121500
  • (附源码)springboot工单管理系统 毕业设计 964158
  • (十一)手动添加用户和文件的特殊权限
  • (转)ObjectiveC 深浅拷贝学习
  • (转)关于如何学好游戏3D引擎编程的一些经验
  • .Net Redis的秒杀Dome和异步执行
  • .NET 的程序集加载上下文
  • .net 无限分类
  • .NET 依赖注入和配置系统
  • .net 重复调用webservice_Java RMI 远程调用详解,优劣势说明
  • @Autowired 与@Resource的区别