php下api接口的并发http请求 ,提高app一个页面请求多个api接口,页面加载慢的问题;

func_helper.php
/**
* 并发http请求
*
* [
* 'url' //请求地址
* 'method' //请求类型 默认为 get 请求
* 'params'
* ]
*/
if(!function_exists('multi_curl_smt')) {
function multi_curl_smt($requests = [])
{
$response = [];
$hander = [];
$mh = curl_multi_init(); foreach($requests as $id=>$item) {
if(empty($item['url'])) {
throw new \Exception('基本参数URL不能为空');
} $ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $item['url']);
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER,1); curl_setopt($ch, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_0);
curl_setopt($ch, CURLOPT_HTTPHEADER, array('Expect: '));
if(defined('CURLOPT_IPRESOLVE') && defined('CURL_IPRESOLVE_V4')){
curl_setopt($ch, CURLOPT_IPRESOLVE, CURL_IPRESOLVE_V4);
}
curl_setopt($ch, CURLOPT_TIMEOUT, isset($item['timeout']) ? $item['timeout'] : 3);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, isset($item['method']) ? $item['method'] : 'GET'); //设置请求参数
if(isset($item['data'])) {
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($item['data']));
} //暂时屏蔽代理服务器
//ENVIRONMENT == 'development' && curl_setopt($ch, CURLOPT_PROXY, '127.0.0.1:8888'); //设置代理服务器
curl_setopt($ch, CURLOPT_HTTPAUTH, CURLAUTH_DIGEST); if(defined('API_USERNAME') && defined('API_PASSWORD')) {
curl_setopt($ch, CURLOPT_USERPWD, API_USERNAME . ":" . API_PASSWORD);
} curl_multi_add_handle($mh,$ch);
$hander[$id] = $ch;
} $running=null;
do {
usleep(1000);
curl_multi_exec($mh,$running);
} while ($running > 0); //get content and remote handle
foreach($hander as $id=>$ch) {
$response[$id] = curl_multi_getcontent($ch);
//检查结果是否需要转换为json, 默认转换
$toArray = isset($requests[$id]['to_array']) ? $requests[$id]['to_array'] == true : true;
if($toArray) {
//$response[$id] = json_decode(trim($data, chr(239) . chr(187) . chr(191)), true);
$response[$id] = json_decode($response[$id], true);
}
curl_multi_remove_handle($mh, $ch);
}
curl_multi_close($mh); //检查是否进行数组转换, 默认转换为数组 return $response;
} 调用
shop.php
public function index()
{ $param= '';
$class_id = null;
if ($key = trim($this->input->get('key')))
{
$param .= '/key/'.urlencode($key); }
if ($class_id = $this->input->get('shop_class_id2'))
{
$param .= '/shop_class/'.$class_id;
}elseif ($class_id = $this->input->get('shop_class_id'))
{
$param .= '/shop_class/'.$class_id;
} if ($this->cur_page)
{
$param .= '/page/'.$this->cur_page;
}
if ($this->per_page)
{
$param .= '/limit/'.$this->per_page;
}
以上是api接口的并发http请求的一个方法   直接复制可以用,
------------------------------------------------------------------------------ 下面是调用api接口的并发http请求方法的例子 ,

    //门店分类

    $multiParams = [];

    $store_id= $this->aSession['store_id'];
$multiParams['shop_class']= $this->_shop_class();
$multiParams['shop_class_children']= $this->_shop_class_children();
$multiParams['shop_store']= $this->_shop_store($store_id); $result = multi_curl_smt($multiParams);
//处理返回结果 //获取一级分类
$shop_class['data'] = $result['shop_class']['data']; if(!isset( $shop_class['data']))
{
$shop_class['data'] = '';
}
//门店所有分类
$shop_class_children['data'] = $result['shop_class_children']['data']; if(!isset($shop_class_children['data']))
{
$shop_class['data'] = '';
} //当前店铺下所有的门店
$shop_store = $result['shop_store']['data'];
if(empty($shop_store))
{
$temp = null;
}else
{
$temp = $shop_store;
}
if ($this->aSession['group_id'] == 1)
{
$shop_list_url = $this->config->item('shop_all_store', 'api_url').'/store_id/'.$this->aSession['store_id'].$param;
$shop_list = curl_smt($shop_list_url); }else{
//获取门店列表
$shop_list_url = $this->config->item('shop_list', 'api_url').'/seller_id/'.$this->aSession['seller_id'].$param;
$shop_list = curl_smt($shop_list_url);
} //数据整理
$list = array();
if ($shop_list['error'] == 'ok' && $shop_class_children['data'] != "" )
{
$tem = $shop_list['data']['list']; foreach ($tem as $k => $val)
{ foreach ($temp as $v1)
{
//找出上级门店
if ($tem[$k]['shop_parent_id'] == $v1['shop_id'])
{
$tem[$k]['shop_parent_id'] = $v1['shop_name'];
}
}
foreach ($shop_class_children['data'] as $v)
{
if ($tem[$k]['shop_class_id'] == $v['class_id'])
{
$tem[$k]['shop_class_id'] = $v['class_name'];
}
}
$saas_order_db=$this->load->database('saas',TRUE);
$store_info = $saas_order_db->from('store')->where(array('store_id'=>$val['store_id']))->select('store_name')->get()->row_array();
if ($store_info) {
$tem[$k]['store_name'] = $store_info['store_name'] ;
}
}
$list = $tem;
$this->aData['pagination'] = $this->page_div($shop_list['data']['total']);
} $page= isset($shop_list['data'])? ceil($shop_list['data']['total'] / $this->per_page):0;
$this->load->vars('shop_name', $key);
$this->load->vars('class_id', $class_id);
$this->load->vars('shop_class', $shop_class['data']);
$this->load->vars('list', $list);
$this->load->vars('page', $page);
$this->load->view('store/shop_index',$this->aData);}

/**
* 以下为接口的请求数据的条件和url地址
*
**/
//(条件)
private function _shop_class(){
$where = array();
return ['url'=>$this->config->item('shop_class_children', 'api_url').'/class_parent_id/1', 'data'=>$where];} //(条件)
private function _shop_store($store_id){
$where = array();
$field ='shop_name';
return ['url'=>$this->config->item('shop_all_store', 'api_url').'/all/1/store_id/'.$store_id.'/field/'.$field, 'data'=>$where];
}
//(条件)
private function _shop_class_children(){
$where = array();
$where['class_parent_id']='';
return ['url'=>$this->config->item('shop_class_children', 'api_url'), 'data'=>$where];
}
 

php下api接口的并发http请求的更多相关文章

  1. App后台开发运维和架构实践学习总结(3)——RestFul架构下API接口设计注意点

    1. 争取相容性和统一性 这里就要求让API设计得是可预测的.按照这种方式写出所有接口和接口所需要的参数.现在就要确保命名是一致的,接口所需的参数顺序也是一致的.你现在应该有products,orde ...

  2. 大叔也说Xamarin~Android篇~调用远程API接口,发POST请求

    回到目录 Xamarin我们在上节已经教大家如何去部署它的环境了,今天来说一个实际的例子,使用android客户调用.net web api的一个接口,并发送POST请求,当服务端回到请求后做出响应, ...

  3. Spring框架下的 “接口调用、MVC请求” 调用参数、返回值、耗时信息输出

    主要拦截前端或后天的请求,打印请求方法参数.返回值.耗时.异常的日志.方便开发调试,能很快定位到问题出现在哪个方法中. 前端请求拦截,mvc的拦截器 import java.util.Date; im ...

  4. 从api接口获取数据-okhttp

    首先先介绍下api接口: API:应用程序接口(API:Application Program Interface) 通常用于数据连接,调用函数提供功能等等... 从api接口获取数据有四种方式:Ht ...

  5. HTTP API接口安全设计

    HTTP API接口安全设计 API接口调用方式 HTTP + 请求签名机制   HTTP + 参数签名机制 HTTPS + 访问令牌机制 有没有更好的方案? OAuth授权机制 OAuth2.0服务 ...

  6. API 接口的安全设计验证:ticket,签名,时间戳

    一.背景 1.与前端对接的API接口,如果被第三方抓包并进行恶意篡改参数,可能会导致数据泄露,甚至会被篡改数据 2.与第三方公司的接口对接,第三方如果得到你的接口文档,但是接口确没安全校验,是十分不安 ...

  7. 亿级用户下的新浪微博平台架构 前端机(提供 API 接口服务),队列机(处理上行业务逻辑,主要是数据写入),存储(mc、mysql、mcq、redis 、HBase等)

    https://mp.weixin.qq.com/s/f319mm6QsetwxntvSXpKxg 亿级用户下的新浪微博平台架构 炼数成金前沿推荐 2014-12-04 序言 新浪微博在2014年3月 ...

  8. Http下的各种操作类.WebApi系列~通过HttpClient来调用Web Api接口

    1.WebApi系列~通过HttpClient来调用Web Api接口 http://www.cnblogs.com/lori/p/4045413.html HttpClient使用详解(java版本 ...

  9. 使用HttpWebRequest请求API接口以及其他网站资源

    很多时候,我们项目需要其他网站的资源,而这个被请求的网站可能属于你们自己开发管理的网站.也可能是公网上其他网站对外开发的API接口,比如说腾讯的微信公众平台的API接口.各大短信服务商的短信API接口 ...

随机推荐

  1. 2019牛客暑期多校训练营(第十场)J - Wood Processing (斜率优化DP)

    >传送门< 题意 $n$个宽度为$w_{i}$,高为$h_{i}$ 的 木块,要求分成$k$组,对于每组内的所有木块,高度都变为组内最低木块的高度,宽度保持不变,求变化的最小面积. 分析 ...

  2. Centos知识

    1.看系统的版本: cat /etc/redhat-release 2.看内核版本: uname -r 3.查看系统是32位还是64位 uname - m 4.磁盘: 磁盘分区有主分区.扩展分区和逻辑 ...

  3. 启xin宝app的token算法破解——frida篇(四)

    前两篇文章分析该APP的抓包.的逆向: 启xin宝app的token算法破解--抓包分析篇(一) 启xin宝app的token算法破解--逆向篇(二) 启xin宝app的token算法破解--toke ...

  4. c++中strcmp,strcopy函数的使用

    1.strcmp(str1,str2) C/C++函数,比较两个字符串, 设这两个字符串为str1,str2,若str1==str2,则返回零:若str1<str2,则返回负数:若str1> ...

  5. alter add命令用来增加表的字段

    alter add命令格式:alter table 表名 add字段 类型 其他; 例如,在表MyClass中添加了一个字段passtest,类型为int(4),默认值为0: mysql> al ...

  6. unity编辑器扩展_07(创建对话框,检测按钮的点击,点击按钮后提示信息,保存设置的数据,显示点击按钮后的处理的进度条信息)

    代码: using UnityEditor;using UnityEngine; public class ChangeValue : ScriptableWizard {               ...

  7. Java集合框架之List接口浅析

    Java集合框架之List接口浅析 一.List综述: 毫无疑问List接口位于java.util包下,继承自 Collection接口 存储元素的特点: 有序可重复(有序:即存进去是什么顺序,取出来 ...

  8. Leetcode之深度优先搜索&回溯专题-679. 24 点游戏(24 Game)

    Leetcode之深度优先搜索&回溯专题-679. 24 点游戏(24 Game) 深度优先搜索的解题详细介绍,点击 你有 4 张写有 1 到 9 数字的牌.你需要判断是否能通过 *,/,+, ...

  9. Leetcode之回溯法专题-131. 分割回文串(Palindrome Partitioning)

    Leetcode之回溯法专题-131. 分割回文串(Palindrome Partitioning) 给定一个字符串 s,将 s 分割成一些子串,使每个子串都是回文串. 返回 s 所有可能的分割方案. ...

  10. javaScript 基础知识汇总(四)

    1.对象 概念:对象可以通过花括号{...} 和其中包含一些可选的属性来创建. 属性时一个键值对,键是一个字符串,值可以是任何类型. 对象的创建 let user = new Object(); // ...