libcurl网络库的函数接口使用

文章目录

  • 1、libcurl简介
  • 2、libcurl的使用
  • 3、函数简介
  • 4、 curl_easy_setopt函数部分选项介绍
  • 5、curl_easy_perform 函数说明(error 状态码)
  • 6、简单实例,包含库文件,头文件即可

1、libcurl简介

libcurl是一个跨平台的网络协议库,支持http, https, ftp, gopher, telnet, dict, file, 和ldap 协议。libcurl同样支持HTTPS证书授权,HTTP POST, HTTP PUT, FTP 上传, HTTP基本表单上传,代理,cookies,和用户认证。

2、libcurl的使用

/** NAME curl_global_init()** DESCRIPTION** curl_global_init() should be invoked exactly once for each application that* uses libcurl and before any call of other libcurl functions.** This function is not thread-safe!*/
CURL_EXTERN CURLcode curl_global_init(long flags);
  • curl_global_init(long flags)

    初始化libcurl。调用curl_easy_init() 函数得到 easy interface型指针。

  • curl_easy_setopt()
    设置传输选项。根据curl_easy_setopt() 设置的传输选项,实现回调函数以完成用户特定任务

  • curl_easy_perform()
    调用curl_easy_perform() 函数完成传输任务。

  • curl_easy_cleanup()
    调用curl_easy_cleanup() 释放内存。

3、函数简介

  • CURLcode curl_global_init(long flags); 函数只能用一次。(其实在调用curl_global_cleanup() 函数后仍然可再用)

如果这个函数在curl_easy_init()函数调用时还没调用,它讲由libcurl库自动调用,所以多线程下最好主动调用该函数以防止在线程中curl_easy_init() 时多次调用。

注意:虽然libcurl是线程安全的,但curl_global_init()是不能保证线程安全的,所以不要在每个线程中都调用curl_global_init(),应该将该函数的调用放在主线程中。

参数:flags

CURL_GLOBAL_ALL //初始化所有的可能的调用。
CURL_GLOBAL_SSL //初始化支持 安全套接字层。
CURL_GLOBAL_WIN32 //初始化win32套接字库。
CURL_GLOBAL_NOTHING //没有额外的初始化。

  • void curl_global_cleanup(void);

结束libcurl使用的时候,用来对curl_global_init()做的工作清理。类似于close的函数。

注意:虽然libcurl是线程安全的,但curl_global_cleanup()是不能保证线程安全的,所以不要在每个线程中都调用curl_global_init(),应该将该函数的调用放在主线程中。

  • char *curl_version( );

打印当前libcurl库的版本。

  • CURL * curl_easy_init( );

curl_easy_init()用来初始化一个CURL的指针(有些像返回FILE类型的指针一样). 相应的在调用结束时要用curl_easy_cleanup() 函数清理。

一般curl_easy_init()意味着一个会话的开始. 它会返回一个easy_handle(CURL*对象), 一般都用在easy系列的函数中。

  • void curl_easy_cleanup(CURL *handle);

这个调用用来结束一个会话.与curl_easy_init() 配合着用。

参数:CURL类型的指针.

  • CURLcode curl_easy_setopt(CURL *handle, CURLoption option, parameter);

这个函数最重要了。几乎所有的libcurl 程序都要频繁的使用它.它告诉curl库,程序将有如何的行为. 比如要查看一个网页的html代码等.(这个函数有些像ioctl函数)参数:

1.CURL类型的指针
2.各种CURLoption类型的选项.(都在curl.h库里有定义,man 也可以查看到)
3.parameter 这个参数 既可以是个函数的指针,也可以是某个对象的指针,也可以是个long型的变量.它用什么这取决于第二个参数.
CURLoption 这个参数的取值很多.具体的可以查看man手册.

  • CURLcode curl_easy_perform(CURL *handle);

在初始化CURL类型的指针 以及curl_easy_setopt()完成后调用. 就像字面的意思所说perform就像是个舞台.让我们设置的option 运作起来。

参数:CURL类型的指针。

4、 curl_easy_setopt函数部分选项介绍

本节主要介绍curl_easy_setopt()中跟http相关的参数。该函数是curl中非常重要的函数,curl所有设置都是在该函数中完成的,该函数的设置选项众多,注意本节的阐述的只是部分常见选项。1和2条为重点。

  • CURLOPT_URL

设置访问URL

  • CURLOPT_WRITEFUNCTION

CURLOPT_WRITEDATA

回调函数原型为:size_t function( void * ptr, size_t size, size_t nmemb, void * stream); 函数将在 libcurl 接收到数据后被调用,因此函数多做数据保存的功能,如处理下载文件。CURLOPT_WRITEDATA 用于表明CURLOPT_WRITEFUNCTION函数中的stream指针的来源。

如果你没有通过CURLOPT_WRITEFUNCTION属性给easy handle设置回调函数,libcurl会提供一个默认的回调函数,它只是简单的将接收到的数据打印到标准输出。你也可以通过 CURLOPT_WRITEDATA属性给默认回调函数传递一个已经打开的文件指针,用于将数据输出到文件里。

CURLOPT_HEADERFUNCTION
CURLOPT_HEADERDATA

回调函数原型为 size_t function( void ptr, size_t size,size_t nmemb, void stream); libcurl一旦接收到http** 头部数据后将调用该函数。CURLOPT_WRITEDATA 传递指针给libcurl,该指针表明CURLOPT_HEADERFUNCTION 函数的 stream 指针的来源。

CURLOPT_READFUNCTION
CURLOPT_READDATA

libCurl需要读取数据传递给远程主机时将调用CURLOPT_READFUNCTION指定的函数,函数原型是: size_t function( void ptr, size_t size,size_t nmemb, void stream); CURLOPT_READDATA 表明CURLOPT_READFUNCTION**函数原型中的 stream指针来源。

CURLOPT_TIMEOUT
CURLOPT_CONNECTIONTIMEOUT

  • CURLOPT_TIMEOUT 由于设置传输时间,CURLOPT_CONNECTIONTIMEOUT 设置连接等待时间。

CURLOPT_FOLLOWLOCATION

5、curl_easy_perform 函数说明(error 状态码)

该函数是完成curl_easy_setopt()指定的所有选项,本节重点介绍curl_easy_perform()的返回值。返回0意味一切ok,非0代表错误发生。主要错误码说明:

  • CURLE_OK
    任务完成一切都好。
  • CURLE_UNSUPPORTED_PROTOCOL
    不支持的协议,由URL的头部指定。
  • CURLE_COULDNT_CONNECT
    不能连接到remote 主机或者代理。
  • CURLE_REMOTE_ACCESS_DENIED
    访问被拒绝。
  • CURLE_HTTP_RETURNED_ERROR
    Http返回错误。
  • CURLE_READ_ERROR
    读本地文件错误。

要获取详细的错误描述字符串,可以通过const char *curl_easy_strerror(CURLcode errornum ) 这个函数取得。

6、简单实例,包含库文件,头文件即可

  • 获取html网页
    在这里插入图片描述
    在这里插入图片描述
#include <stdio.h>
#include <curl/curl.h>
#include <stdlib.h>
int main(int argc, char *argv[])
{CURL *curl;             //定义CURL类型的指针CURLcode res;           //定义CURLcode类型的变量,保存返回状态码if (argc != 2){printf("Usage : file <url>;\n");exit(1);}curl = curl_easy_init();        //初始化一个CURL类型的指针if (curl != NULL){//设置curl选项. 其中CURLOPT_URL是让用户指 定url. argv[1]中存放的命令行传进来的网址curl_easy_setopt(curl, CURLOPT_URL, argv[1]);//调用curl_easy_perform 执行我们的设置.并进行相关的操作. 在这 里只在屏幕上显示出来.res = curl_easy_perform(curl);//清除curl操作.curl_easy_cleanup(curl);}return 0;
}

在这里插入图片描述
在这里插入图片描述

输出结果:
在这里插入图片描述

  • 基本的http GET/POST操作
#include <stdio.h>
#include <curl/curl.h>
bool getUrl(char *filename)
{CURL *curl;CURLcode res;FILE *fp;if ((fp = fopen(filename, "w")) == NULL)  // 返回结果用文件存储return false;struct curl_slist *headers = NULL;headers = curl_slist_append(headers, "Accept: Agent-007");curl = curl_easy_init();    // 初始化if (curl){//curl_easy_setopt(curl, CURLOPT_PROXY, "10.99.60.201:8080");// 代理curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);// 改协议头curl_easy_setopt(curl, CURLOPT_URL, "http://www.baidu.com");curl_easy_setopt(curl, CURLOPT_WRITEDATA, fp); //将返回的http头输出到fp指向的文件curl_easy_setopt(curl, CURLOPT_HEADERDATA, fp); //将返回的html主体数据输出到fp指向的文件res = curl_easy_perform(curl);   // 执行if (res != 0) {curl_slist_free_all(headers);curl_easy_cleanup(curl);printf("111");}fclose(fp);return true;}return false;
}
bool postUrl(char *filename)
{CURL *curl;CURLcode res;FILE *fp;if ((fp = fopen(filename, "w")) == NULL)return false;curl = curl_easy_init();if (curl){curl_easy_setopt(curl, CURLOPT_COOKIEFILE, "cookie.txt"); // 指定cookie文件curl_easy_setopt(curl, CURLOPT_POSTFIELDS, "&logintype=uid&u=xieyan&psw=xxx86");    // 指定post内容//curl_easy_setopt(curl, CURLOPT_PROXY, "10.99.60.201:8080");curl_easy_setopt(curl, CURLOPT_URL, " http://mail.sina.com.cn/cgi-bin/login.cgi ");   // 指定urlcurl_easy_setopt(curl, CURLOPT_WRITEDATA, fp);res = curl_easy_perform(curl);curl_easy_cleanup(curl);}fclose(fp);return true;
}
int main(void)
{getUrl("get.html");postUrl("post.html");return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/27136.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

消息队列(3) -封装数据库的操作

前言 上一篇博客我们写了, 关于交换机, 队列,绑定, 写入数据库的一些建库建表的操作 这一篇博客中,我们将建库建表操作,封装一下实现层一个类来供上层服务的调用 , 并在写完该类之后, 测试代码是否完整 实现封装 在写完上述的接口类 与 xml 后, 我们想要 创建一个类 ,来调用…

uniapp实现支付宝菜单展开与收起

需求实现支付宝类似的效果&#xff1a; 思路&#xff1a; 1.首先建立展开收起按钮&#xff0c;这里使用的是uview里面的icon图标。 2.其次建立展开菜单内容&#xff0c;这里只演示了文本信息&#xff0c;后期引入首页应用。 3.最后写js逻辑&#xff0c;展开收起时改变盒子高度和…

基于STM32设计的出租车计费系统

一、项目介绍 在城市交通中&#xff0c;出租车是一种常见的交通工具。为了方便乘客和司机之间的交易&#xff0c;出租车计费系统被广泛应用于出租车行业。系统能够自动计算乘客的费用&#xff0c;提供准确、方便的计费服务&#xff0c;并且能够记录乘客的行驶数据&#xff0c;…

flink kafka消费者如何处理kafka主题的rebalance

背景&#xff1a; 我们日常使用kafka客户端消费kafka主题的消息时&#xff0c;当消费者退出/加入消费者组&#xff0c;kafka主题分区数有变等事件发生时&#xff0c;都会导致rebalance的发生&#xff0c;此时一般情况下&#xff0c;如果我们不自己处理offset&#xff0c;我们不…

django处理分页

当数据库量比较大的时候一定要分页查询的 在django中操作数据库进行分页 queryset models.PrettyNum.objects.all() #查询所有 queryset models.PrettyNum.objects.all()[0:10] #查询出1-10列 queryset models.PrettyNum.objects.filter(mobile__contains136)[0:10] …

python-opencv对极几何 StereoRectify

OpenCV如何正确使用stereoRectify函数 函数介绍 用于双目相机的立体校正环节中&#xff0c;这里只谈谈这个函数怎么使用&#xff0c;参数具体指哪些函数参数 随便去网上一搜或者看官方手册就能得到参数信息&#xff0c;但是&#xff01;&#xff01;相对关系非常容易出错&…

机器学习深度学习——池化层

&#x1f468;‍&#x1f393;作者简介&#xff1a;一位即将上大四&#xff0c;正专攻机器学习的保研er &#x1f30c;上期文章&#xff1a;机器学习&&深度学习——卷积的多输入多输出通道 &#x1f4da;订阅专栏&#xff1a;机器学习&&深度学习 希望文章对你们…

1. Git基础知识

文章目录 Git基础知识一、集中式与分布式二、中心服务器三、工作流四、分支实现五、冲突六、Fast forward七、储藏&#xff08;Stashing&#xff09;八、SSH 传输设置九、.gitignore 文件十、Git 命令一览十一、和远端仓库交互 Git基础知识 一、集中式与分布式 Git 属于分布式…

【单片机】51单片机,晨启科技,板子引脚对应关系

一般引脚: sbit beepP2^4; //将单片机的P2.4端口定义为beep.本口用于屏蔽上电后蜂鸣器响 sbit ledP1^0; //将单片机的P1.0端口定义为led&#xff0c;用于点亮LED-D1 sbit DIG1P0^0; //数码管位选1 sbit DIG2P0^1; //数码管位选2P10xFF;//初始化P1引脚全部置高&a…

【第一阶段】kotlin的when表达式

1.Java 的if /when是语句 kotlin的if/when是表达式&#xff0c;表达式是有返回值的 java中void是个关键字&#xff0c;Unit在kotlin中是个类 2.当使用when语句的时候必须有一个不满足的值即else: fun main() {var week:Int5val info when(week){1->"今天是星期一"…

Transformer学习笔记

Transformer学习笔记 前言前提条件相关介绍Transformer总体架构编码器&#xff08;Encoder&#xff09;位置编码&#xff08;Positional Encoding&#xff09;get_attn_pad_mask函数&#xff08;Padding Mask&#xff09;EncoderLayerMultiHeadAttentionScaledDotProductAttent…

项目出bug,找不到bug,如何拉回之前的版本

1.用gitee如何拉取代码 本文为转载于「闪耀太阳a」的原创文章原文链接&#xff1a;https://blog.csdn.net/Gufang617/article/details/119929145 怎么从gitee上拉取代码 1.首先找到gitee上想要拉取得代码URL地址 点击复制这里的https地址 1 ps:&#xff08;另外一种方法&…

xcode打包导出ipa

转载&#xff1a;xcode打包导出ipa 目录 转载&#xff1a;xcode打包导出ipa 第一步&#xff1a;注册苹果开发者账号 第二步&#xff1a;下载APP Uploader 第三步&#xff1a;使用xcode打包导出ipa文件&#xff0c;供其他人内测 众所周知&#xff0c;在开发苹果应用时需要使…

Leetcode31 下一个排列

解题思路&#xff1a; 算法过程的第二步&#xff0c;可以变为将[j,end]排序&#xff0c;然后从[j,end)和i进行比较&#xff0c;在区间j,end区间第一个大于nums[i]后&#xff0c;交换即可 public void nextPermutation(int[] nums) {int len nums.length - 1;for(int i len;i…

【电机绘图】:插补算法(一)—直线插补—逐点比较法

今日介绍学习一种使用电机作画、绘图、加工零件时需要使用的算法 &#xff1a; 插补算法 本文提供直线插补的概念基础&#xff0c;基本思路分析&#xff0c;C语言实现等&#xff0c;代码会直接贴出&#xff01; 插补算法是指在数值计算或数据处理中&#xff0c;根据已有的数据…

单例模式(C++)

定义 保证一个类仅有一个实例&#xff0c;并提供一个该实例的全局访问点。 应用场景 在软件系统中&#xff0c;经常有这样一些特殊的类,必须保证它们在系统中只存在一个实例&#xff0c;才能确保它们的逻辑正确性、以及良好的效率。如何绕过常规的构造器&#xff0c;提供一种…

Babel编译与Webpack

目录 Babel初识BabelBabel 使用方式使用 Babel 前的准备工作 WebpackWebpack介绍Webpack初体验Webpack核心概念入口&#xff08;entry&#xff09;出口&#xff08;output&#xff09;加载 (loader)插件&#xff08;plugins&#xff09; Babel Babel官网: https://babeljs.io/…

【Hystrix技术指南】(6)请求合并机制原理分析

[每日一句] 也许你度过了很糟糕的一天&#xff0c;但这并不代表你会因此度过糟糕的一生。 [背景介绍] 分布式系统的规模和复杂度不断增加&#xff0c;随着而来的是对分布式系统可用性的要求越来越高。在各种高可用设计模式中&#xff0c;【熔断、隔离、降级、限流】是经常被使…

小白到运维工程师自学之路 第六十四集 (dockerfile构建tomcat、mysql、lnmp、redis镜像)

一、tomcat&#xff08;更换jdk&#xff09; mkdir tomcat cd tomcat/ tar xf jdk-8u191-linux-x64.tar.gz tar xf apache-tomcat-8.5.40.tar.gzvim Dockerfile FROM centos:7 MAINTAINER Crushlinux <syh163.com> ADD jdk1.8.0_191 /usr/local/java ENV JAVA_HOME /us…

国内大模型在局部能力上已超ChatGPT

中文大模型正在后来居上&#xff0c;也必须后来居上。 数科星球原创 作者丨苑晶 编辑丨大兔 从GPT3.5彻底出圈后&#xff0c;大模型的影响力开始蜚声国际。一段时间内&#xff0c;国内科技公司可谓被ChatGPT按在地上打&#xff0c;毫无还手之力。 彼时&#xff0c;很多企业…