HTTP/存储/Ajax

前后端数据交互与HTTP协议
===================================前后端通信====================================
1、前后端通信是什么
前端和后端数据交互的过程
浏览器和服务器之间数据交
2、前后端通信的过程
前后端的通信是在‘请求-响应’中完成的
3、概念解释
前端:浏览器端
客户端:只要能和服务器通信的就叫 客户端
后端:服务器端
4、使用浏览器访问网页
在浏览器地址栏输入网址,按下回车
5、HTML 的标签
浏览器在解析 HTML 标签的时候,遇到一些特殊的标签,会再次向服务器发送请求
link/img/script/iframe
6、还有一些标签,浏览器解析的时候,不会向服务器发送请求,但是用户可以使用他们向服务器发送请求
a/form
7、Ajax 和 Fetch

===============================初识HTTP=======================================

1、HTTP 是什么
HyperText Transfer Protocol
超文本传输协议
HTML:超文本标记语言
超文本:原先一个个单一的文本,通过超链接将其联系起来。由原先的单一的文本变成了可无限延伸、扩展的超级文本、立体文本
HTML、JS、CSS、图片、字体、音频、视频等等文件,都是通过 HTTP(超文本传输协议) 在服务器和浏览器之间传输
每一次前后端通信,前端需要主动向后端发出请求,后端接收到前端的请求后,可以给出响应
HTTP 是一个请求-

2、HTTP 报文是什么
浏览器向服务器发送请求时,请求本身就是信息,叫请求报文
服务器向浏览器发送响应时传输的信息,叫响应报文

3、HTTP 报文格式
请求
请求头:起始行+首部
请求体
GET 请求,没有请求体,数据通过请求头携带
POST 请求,有请求体,数据通过请求体携带
响应
响应头:起始行+首部
响应体
4、常用的 HTTP 方法
浏览器发送请求时采用的方法,和响应无关

  GET、POST、PUT、DELETE

  用来定义对于资源采取什么样的操作的,有各自的语义

5、HTTP 方法的语义
GET 获取数据
获取资源(文件)

  POST 创建数据
  注册

  PUT 更新数据
  修改个人信息,修改密码

  DELETE 删除数据
  删除一条评论

  增删改查

  这些方法虽然有各自的语义,但是并不是强制性的

6、RESTful 接口设计
一种接口设计风格,充分利用 HTTP 方法的语义

  通过用户 ID 获取个人信息,使用 GET 方法
  https://www.imooc.com/api/http/getUser?id=1

  GET
  https://www.imooc.com/api/http/user?id=1

  注册新用户,使用 POST 方法
  https://www.imooc.com/api/http/addUser

  POST
  https://www.imooc.com/api/http/user

  修改一个用户,使用 POST 方法
  https://www.imooc.com/api/http/modifyUser

  PUT
  https://www.imooc.com/api/http/user

  删除一个用户,使用 POST 方法
  https://www.imooc.com/api/http/deleteUser

  DELETE
  https://www.imooc.com/api/http/user

7、GET和POS
语义
GET:获取数据
POST:创建数据

8、发送数据
GET 通过地址在请求头中携带数据
能携带的数据量和地址的长度有关系,一般最多就几K

  POST 既可以通过地址在请求头中携带数据,也可以通过请求体携带数据
  能携带的数据量理论上是无限的

  携带少量数据,可以使用 GET 请求,大量的数据可以使用 POST 请求

9、缓存
GET 可以被缓存,POST 不会被缓存

10、安全性
GET 和 POST 都不安全

  发送密码或其他敏感信息时不要使用 GET,主要是避免直接被他人窥屏或通过历史记录找到你的密码

11、HTTP 状态码是什么
定义服务器对请求的处理结果,是服务器返回的

12、HTTP 状态码的语义
100~199 消息:代表请求已被接受,需要继续处理
websocket

  200~299 成功
  200

  300~399 重定向
  http://www.imooc.com/
  https://www.imooc.com/

  301 Moved Permanently
  302 Move Temporarily
  304 Not Modifie

  400~499 请求错误
  404 Not Found

  500~599 服务器错误
  500 Internal Server Error

===============================本地存储=================================
1、Cookie 是什么
Cookie 全称 HTTP Cookie,简称 Cookie
是浏览器存储数据的一种方式
因为存储在用户本地,而不是存储在服务器上,是本地存储
一般会自动随着浏览器每次请求发送到服务器端

2、Cookie 有什么用
利用 Cookie 跟踪统计用户访问该网站的习惯,比如什么时间访问,访问了哪些页面,在每个网页的停留时间等

3、在浏览器中操作 Cookie
不要在 Cookie 中保存密码等敏感信息

4、写入 Cookie
document.cookie = 'username=zs';
document.cookie = 'age=18';
不能一起设置,只能一个一个设置
document.cookie = 'username=zs; age=18';

5、读取 Cookie
console.log(document.cookie);
读取的是一个由名值对构成的字符串,每个名值对之间由“; ”(一个分号和一个空格)隔开
username=zs; age=18
6、Cookie 的名称(Name)和值(Value)
最重要的两个属性,创建 Cookie 时必须填写,其它属性可以使用默认值

  Cookie 的名称或值如果包含非英文字母,则写入时需要使用 encodeURIComponent() 编码,读取时使用 decodeURIComponent() 解码
  document.cookie = 'username=alex';

  document.cookie = `username=${encodeURIComponent('张三')}`;
  document.cookie = `${encodeURIComponent('用户名')}=${encodeURIComponent(
    '张三'
  )}`;

  一般名称使用英文字母,不要用中文,值可以用中文,但是要编码

7、失效(到期)时间
对于失效的 Cookie,会被浏览器清除
如果没有设置失效(到期)时间,这样的 Cookie 称为会话 Cookie
它存在内存中,当会话结束,也就是浏览器关闭时,Cookie 消失

  document.cookie = 'username=alex';

  想长时间存在,设置 Expires 或 Max-Age
  expires
  值为 Date 类型
  document.cookie = `username=alex; expires=${new Date(
    '2100-1-01 00:00:00'
  )}`;

  max-age
  值为数字,表示当前时间 + 多少秒后过期,单位是秒
  document.cookie = 'username=alex; max-age=5';
  document.cookie = `username=alex; max-age=${24 * 3600 * 30}`;

  如果 max-age 的值是 0 或负数,则 Cookie 会被删除
  document.cookie = 'username=alex';
  document.cookie = 'username=alex; max-age=0';
  document.cookie = 'username=alex; max-age=-1';

8、Domain 域
Domain 限定了访问 Cookie 的范围(不同域名)

  使用 JS 只能读写当前域或父域的 Cookie,无法读写其他域的 Cookie
  document.cookie = 'username=alex; domain=www.imooc.com';
  www.imooc.com m.imooc.com 当前域
  父域:.imooc.com

9、Path 路径
Path 限定了访问 Cookie 的范围(同一个域名下)

  使用 JS 只能读写当前路径和上级路径的 Cookie,无法读写下级路径的 Cookie
  document.cookie = 'username=alex; path=/course/list';
  document.cookie = 'username=alex; path=/1.Cookie/';
  当 Name、Domain、Path 这 3 个字段都相同的时候,才是同一个 Cookie

6、HttpOnly
设置了 HttpOnly 属性的 Cookie 不能通过 JS 去访问

7、Secure 安全标志
Secure 限定了只有在使用了 https 而不是 http 的情况下才可以发送给服务端
Domain、Path、Secure 都要满足条件,还不能过期的 Cookie 才能随着请求发送到服务器端
8、cookie的封装

// 写入 Cookie
const set = (name, value, { maxAge, domain, path, secure } = {}) => {
  let cookieText = `${encodeURIComponent(name)}=${encodeURIComponent(value)}`;

  if (typeof maxAge === 'number') {
    cookieText += `; max-age=${maxAge}`;
  }

  if (domain) {
    cookieText += `; domain=${domain}`;
  }

  if (path) {
    cookieText += `; path=${path}`;
  }

  if (secure) {
    cookieText += `; secure`;
  }

  document.cookie = cookieText;

  // document.cookie='username=alex; max-age=5; domain='
};

// 通过 name 获取 cookie 的值
const get = name => {
  name = `${encodeURIComponent(name)}`;

  const cookies = document.cookie.split('; ');

  for (const item of cookies) {
    const [cookieName, cookieValue] = item.split('=');

    if (cookieName === name) {
      return decodeURIComponent(cookieValue);
    }
  }

  return;
};

// 'username=alex; age=18; sex=male'
// ["username=alex", "age=18", "sex=male"]
// ["username","alex"]

// get('用户名');

// 根据 name、domain 和 path 删除 Cookie
const remove = (name, { domain, path } = {}) => {
  set(name, '', { domain, path, maxAge: -1 });
};

export { set, get, remove };

10、cookie的注意事项
1).前后端都可以创建 Cookie

2).Cookie 有数量限制
  每个域名下的 Cookie 数量有限
  当超过单个域名限制之后,再设置 Cookie,浏览器就会清除以前设置的 Cookie

3).Cookie 有大小限制
  每个 Cookie 的存储容量很小,最多只有 4KB 左右

11、localStorage 是什么
localStorage 也是一种浏览器存储数据的方式(本地存储),它只是存储在本地,不会发送到服务器端
单个域名下的 localStorage 总大小有限制

12、在浏览器中操作 localStorage

13、localStorage 的基本用法
console.log(localStorage);

  // setItem()
  localStorage.setItem('username', 'alex');
  localStorage.setItem('username', 'zs');
  localStorage.setItem('age', 18);
  localStorage.setItem('sex', 'male');

  // length
  // console.log(localStorage.length);

  // getItem()
  // console.log(localStorage.getItem('username'));
  // console.log(localStorage.getItem('age'));

  // // 获取不存在的返回 null
  // console.log(localStorage.getItem('name'));

  // removeItem()
  // localStorage.removeItem('username');
  // localStorage.removeItem('age');

  // // 删除不存在的 key,不报错
  // localStorage.removeItem('name');

  // clear()
  localStorage.clear();

  console.log(localStorage);

14、 localStorage 的注意事项
1)、localStorage 的存储期限
localStorage 是持久化的本地存储,除非手动清除(比如通过 js 删除,或者清除浏览器缓存),否则数据是永远不会过期的

  sessionStorage
  当会话结束(比如关闭浏览器)的时候,sessionStorage 中的数据会被清空
  sessionStorage.setItem('username', 'alex');
  sessionStorage.getItem('username');
  sessionStorage.removeItem('username');
  sessionStorage.clear();

2)、localStorage 键和值的类型
localStorage 存储的键和值只能是字符串类型
不是字符串类型,也会先转化成字符串类型再存进去

  localStorage.setItem({}, 18);
  // localStorage.setItem('students', [{},{}]);
  console.log(
    typeof localStorage.getItem('[object Object]'),
    localStorage.getItem('[object Object]')
  );

  console.log({}.toString());

3)、不同域名下能否共用 localStorage
不同的域名是不能共用 localStorage 的

4)、localStorage 的兼容性
IE7及以下版本不支持 localStorage,IE8 开始支持

====================================Ajax和Fetch基础=============================
1、Ajax 是什么
Ajax 是 Asynchronous JavaScript and XML(异步 JavaScript 和 XML)的简写
Ajax 中的异步:可以异步地向服务器发送请求,在等待响应的过程中,不会阻塞当前页面,浏览器可以做自己的事情。直到成功获取响应后,浏览器才开始处理响应数据
XML(可扩展标记语言)是前后端数据通信时传输数据的一种格式
XML 现在已经不怎么用了,现在比较常用的是 JSON
Ajax 其实就是浏览器与服务器之间的一种异步通信方式
使用 Ajax 可以在不重新加载整个页面的情况下,对页面的某部分进行更新
① 慕课网注册检测
② 慕课网搜索提示
2、搭建 Ajax 开发环境
Ajax 需要服务器环境,非服务器环境下,很多浏览器无法正常使用 Ajax
Live Server
windows phpStudy
Mac MAMP
3、Ajax 的使用步骤
1)创建 xhr 对象
2)监听事件,处理响应
3)准备发送请求
4)发送请求

4、使用 Ajax 完成前后端通信

     const url = 'https://www.imooc.com/api/http/search/suggest?words=js';

     const xhr = new XMLHttpRequest();
     xhr.onreadystatechange = () => {
       if (xhr.readyState !== 4) return;

       if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
         console.log(xhr.responseText);
         console.log(typeof xhr.responseText);
       }
     };
     xhr.open('GET', url, true);  
     xhr.send(null);

5、Get请求
1)、携带数据
GET 请求不能通过请求体携带数据,但可以通过请求头携带
const url = 'https://www.imooc.com/api/http/search/suggest?words=js&username=alex&age=18';
2)、数据编码
如果携带的数据是非英文字母的话,比如说汉字,就需要编码之后再发送给后端,不然会造成乱码问题
可以使用 encodeURIComponent() 编码
6、POST请求
1)携带数据
2)POST 请求主要通过请求体携带数据,同时也可以通过请求头携带
如果想发送数据,直接写在 send() 的参数位置,一般是字符串
不能直接传递对象,需要先将对象转换成字符串的形式
3)数据编码
xhr.send(username=${encodeURIComponent('张三')}&age=18);
7、 JSON 是什么
Ajax 发送和接收数据的一种格式
8、为什么需要 JSON
JSON 有 3 种形式,每种形式的写法都和 JS 中的数据类型很像,可以很轻松的和 JS 中的数据类型互相转换
9、JSON 的 3 种形式
1)简单值形式
.json

  JSON 的简单值形式就对应着 JS 中的基础数据类型
  数字、字符串、布尔值、null

  注意事项
  ① JSON 中没有 undefined 值
  ② JSON 中的字符串必须使用双引号
  ③ JSON 中是不能注释的

2)对象形式
  JSON 的对象形式就对应着 JS 中的对象

  注意事项
  JSON 中对象的属性名必须用双引号,属性值如果是字符串也必须用双引号
  JSON 中只要涉及到字符串,就必须使用双引号
  不支持 undefined

3)数组形式
  JSON 的数组形式就对应着 JS 中的数组
  [1, "hi", null]
  注意事项
  数组中的字符串必须用双引号
  JSON 中只要涉及到字符串,就必须使用双引号
  不支持 undefined

10、JSON 的常用方法
1)JSON.parse()
JSON.parse() 可以将 JSON 格式的字符串解析成 JS 中的对应值
一定要是合法的 JSON 字符串,否则会报错
2)JSON.stringify()
JSON.stringify() 可以将 JS 的基本数据类型、对象或者数组转换成 JSON 格式的字符串
11、使用 JSON.parse() 和 JSON.stringify() 封装 localStorage

const storage = window.localStorage;

// 设置
const set = (key, value) => {
  // {
  //   username: 'alex'
  // }
  storage.setItem(key, JSON.stringify(value));
};

// 获取
const get = key => {
  // 'alex'
  // {
  //   "username": "alex"
  // }
  return JSON.parse(storage.getItem(key));
};

// 删除
const remove = key => {
  storage.removeItem(key);
};

// 清空
const clear = () => {
  storage.clear();
};

export { set, get, remove, clear };

12、跨域是什么
向一个域发送请求,如果要请求的域和当前域是不同域,就叫跨域
不同域之间的请求,就是跨域请求
13、什么是不同域,什么是同域
协议、域名、端口号,任何一个不一样,就是不同域
与路径无关,路径一不一样无所谓
14、.跨域请求为什么会被阻止
阻止跨域请求,其实是浏览器本身的一种安全策略--同源策略
其他客户端或者服务器都不存在跨域被阻止的问题

15、.跨域解决方案
① CORS 跨域资源共享
② JSONP

  优先使用 CORS 跨域资源共享,如果浏览器不支持 CORS 的话,再使用 JSONP

16、JSONP 的原理
script 标签跨域不会被浏览器阻止
JSONP 主要就是利用 script 标签,加载跨域文件

17、使用 JSONP 实现跨域
服务器端准备好 JSONP 接口
https://www.imooc.com/api/http/jsonp?callback=handleResponse

const script = document.createElement('script');
    script.src =
      'https://www.imooc.com/api/http/jsonp?callback=handleResponse';
    document.body.appendChild(script);

    // 声明函数
    const handleResponse = data => {
      console.log(data);
    };

18、XHR 的属性

1.responseType 和 response 属性
     const url = 'https://www.imooc.com/api/http/search/suggest?words=js';
     const xhr = new XMLHttpRequest();

     xhr.onreadystatechange = () => {
       if (xhr.readyState != 4) return;

       if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
         // 文本形式的响应内容
         // responseText 只能在没有设置 responseType 或者 responseType = '' 或 'text' 的时候才能使用
         // console.log('responseText:', xhr.responseText);

         // 可以用来替代 responseText
         console.log('response:', xhr.response);
         // console.log(JSON.parse(xhr.responseText));
       }
     };
     xhr.open('GET', url, true);

     // xhr.responseType = '';
     // xhr.responseType = 'text';
     xhr.responseType = 'json';

     xhr.send(null);

     IE6~9 不支持,IE10 开始支持

     2.timeout 属性
     设置请求的超时时间(单位 ms)
     const url = 'https://www.imooc.com/api/http/search/suggest?words=js';
     const xhr = new XMLHttpRequest();

     xhr.onreadystatechange = () => {
       if (xhr.readyState != 4) return;

       if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
         console.log(xhr.response);
       }
     };

     xhr.open('GET', url, true);

     xhr.timeout = 10000;

     xhr.send(null);

     IE6~7 不支持,IE8 开始支持

     3.withCredentials 属性
     指定使用 Ajax 发送请求时是否携带 Cookie

     使用 Ajax 发送请求,默认情况下,同域时,会携带 Cookie;跨域时,不会
     xhr.withCredentials = true;
     最终能否成功跨域携带 Cookie,还要看服务器同不同意

     const url = 'https://www.imooc.com/api/http/search/suggest?words=js';
     // const url = './index.html';

     const xhr = new XMLHttpRequest();

     xhr.onreadystatechange = () => {
       if (xhr.readyState != 4) return;

       if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
         console.log(xhr.response);
       }
     };

     xhr.open('GET', url, true);

     xhr.withCredentials = true;

     xhr.send(null);

     IE6~9 不支持,IE10 开始支持

19、XHR 的方法

// 1.abort()
      // 终止当前请求
      // 一般配合 abort 事件一起使用
      // const url = 'https://www.imooc.com/api/http/search/suggest?words=js';

      // const xhr = new XMLHttpRequest();

      // xhr.onreadystatechange = () => {
      //   if (xhr.readyState != 4) return;

      //   if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
      //     console.log(xhr.response);
      //   }
      // };

      // xhr.open('GET', url, true);

      // xhr.send(null);

      // xhr.abort();

      // 2.setRequestHeader()
      // 可以设置请求头信息
      // xhr.setRequestHeader(头部字段的名称, 头部字段的值);
      // const url = 'https://www.imooc.com/api/http/search/suggest?words=js';
      const url = 'https://www.imooc.com/api/http/json/search/suggest?words=js';

      const xhr = new XMLHttpRequest();

      xhr.onreadystatechange = () => {
        if (xhr.readyState != 4) return;

        if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
          console.log(xhr.response);
        }
      };
      xhr.open('POST', url, true);

      // 请求头中的 Content-Type 字段用来告诉服务器,浏览器发送的数据是什么格式的
      // xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
      xhr.setRequestHeader('Content-Type', 'application/json');

      // xhr.send(null);
      // xhr.send('username=alex&age=18');
      xhr.send(
        JSON.stringify({
          username: 'alex'
        })
      );

20、XHR 的事件

 // 1.load 事件
      // 响应数据可用时触发
      // const url = 'https://www.imooc.com/api/http/search/suggest?words=js';
      // const xhr = new XMLHttpRequest();

      // // xhr.onload = () => {
      // //   if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
      // //     console.log(xhr.response);
      // //   }
      // // };
      // xhr.addEventListener(
      //   'load',
      //   () => {
      //     if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
      //       console.log(xhr.response);
      //     }
      //   },
      //   false
      // );

      // xhr.open('GET', url, true);

      // xhr.send(null);

      // IE6~8 不支持 load 事件

      // 2.error 事件
      // 请求发生错误时触发

      // const url = 'https://www.imooc.com/api/http/search/suggest?words=js';
      // const url = 'https://www.iimooc.com/api/http/search/suggest?words=js';
      // const xhr = new XMLHttpRequest();

      // xhr.addEventListener(
      //   'load',
      //   () => {
      //     if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
      //       console.log(xhr.response);
      //     }
      //   },
      //   false
      // );
      // xhr.addEventListener(
      //   'error',
      //   () => {
      //     console.log('error');
      //   },
      //   false
      // );

      // xhr.open('GET', url, true);

      // xhr.send(null);

      // IE10 开始支持

      // 3.abort 事件
      // 调用 abort() 终止请求时触发
      // const url = 'https://www.imooc.com/api/http/search/suggest?words=js';

      // const xhr = new XMLHttpRequest();

      // xhr.addEventListener(
      //   'load',
      //   () => {
      //     if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
      //       console.log(xhr.response);
      //     }
      //   },
      //   false
      // );
      // xhr.addEventListener(
      //   'abort',
      //   () => {
      //     console.log('abort');
      //   },
      //   false
      // );

      // xhr.open('GET', url, true);

      // xhr.send(null);

      // xhr.abort();

      // IE10 开始支持

      // 4.timeout 事件
      // 请求超时后触发
      const url = 'https://www.imooc.com/api/http/search/suggest?words=js';

      const xhr = new XMLHttpRequest();

      xhr.addEventListener(
        'load',
        () => {
          if ((xhr.status >= 200 && xhr.status < 300) || xhr.status === 304) {
            console.log(xhr.response);
          }
        },
        false
      );
      xhr.addEventListener(
        'timeout',
        () => {
          console.log('timeout');
        },
        false
      );

      xhr.open('GET', url, true);

      xhr.timeout = 10;

      xhr.send(null);

21、axios
axios 是什么
axios 是一个基于 Promise 的 HTTP 库,可以用在浏览器和 node.js 中
第三方 Ajax 库

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 205,033评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 87,725评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,473评论 0 338
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,846评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,848评论 5 368
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,691评论 1 282
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,053评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,700评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 42,856评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,676评论 2 323
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,787评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,430评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,034评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,990评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,218评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,174评论 2 352
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,526评论 2 343

推荐阅读更多精彩内容