AgentProxy.h 29.2 KB
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828
/*
 * Copyright 2002-2014 the original author or authors.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      CC/LICENSE
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef AGENTPROXY
#define AGENTPROXY

#ifdef _WIN32
#include <hash_map>

#else
#include <ext/hash_map>
using namespace __gnu_cxx;  //for hash_map
#endif


#include <string>
#include <vector>
#include <time.h>
#include <bgcc.h>


#include "acdcommon.h"
#include "acd.h"
#include "ap.h"

#include "ApCommon.h"
#include "ApClient.h"
#include "ApServer.h"
#include "ApService.h"
#include "Queue.h"
#include "ApCallbackThread.h"
#include "ApHeartBeatThread.h"
#include "ApListenThread.h"

using namespace ap;
using namespace acd;

class ApServer;
class ApClient;
class ApService;

class AgentProxy {
    typedef Guard<Mutex> ScopeGuard;

    /*公有成员接口声明*/
public:
    /**
     * @brief Init:AgentProxy类初始化函数,用于初始化消息队列、hash_map、创建事件线程、读取log、conf配置等功能
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月28日 13时05分33秒
     */
    bool Init();

    /**
     * @brief SetMapAgentIdData:插入一条新的连接数据agentdata
     *
     * @param agentInfo
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 12时59分09秒
     */
    bool SetMapAgentIdData(AgentData* agentInfo);

    /**
     * @brief DelMapAgentIdData:清除指定工号的连接信息
     * @param agentId
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月28日 13时07分04秒
     */
    bool DelMapAgentIdData(const std::string& agentId);

    /**
     * @brief ClearMapAgentData:清空hash_map所有存储信息
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月28日 13时07分04秒
     */
    bool ClearMapAgentData();

    /**
     * @brief ResetProxy:重置指定工号的连接信息
     *
     * @param agentId    指定的工号
     * @param agentInfo  重置的连接信息
     *
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月28日 13时07分30秒
     */
    bool ResetProxy(const std::string& agentId, AgentData* agentInfo);

    /**
     * @brief GetAgentData 获取指定工号的连接信息
     *
     * @param agentId    指定的工号
     * @param agentInfo  获取的连接信息
     *
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月29日 17时23分25秒
     */
    bool GetAgentData(const std::string& agentId, AgentData& agentInfo);

    /**
     * @brief GetAgentData 根据工号获取handle值
     *
     * @param agentId    指定的工号
     * @param agentInfo  输出参数:获取的handle值
     *
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月29日 17时23分25秒
     */
    bool GetAgentHandleById(const std::string agentId, int64_t& handle);

    /**
     * @brief GetAgentData 根据工号查看坐席信息是否存在
     * @param agentId    指定的工号
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月29日 17时23分25秒
     */
    bool IsAgentHasExist(const std::string agentId);

    /**
     * @brief GetAgentData 更新坐席信息
     * @param agentinfo    指定的更新的坐席信息
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2012年06月29日 17时23分25秒
     */
    bool UpdateAgentData(AgentData& agentinfo);

    /**
     * @brief SetAgentOldProxyNull 将oldproxy置空
     * @param agentId          指定的更新的坐席工号
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool SetAgentOldProxyNull(const std::string agentId, int64_t handle);

    /**
     * @brief SetAgentHandleById    更新指定的坐席的handle值
     * @param agentId               指定的坐席工号
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool SetAgentHandleById(const std::string agentId, int64_t handle);

    /**
     * @brief SetAgentFlag          设置指定坐席是否被删除的标志位
     * @param agentId               指定的坐席工号
     * @param flag                  标示是否signout
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void SetAgentFlag(const std::string agentId, int32_t flag);

    /**
     * @brief SendCallEvent         发送呼叫事件处理函数
     * @param acdCallEvent          坐席呼叫事件
     * @param threadNo              处理线程ID
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void SendCallEvent(const AgentEventT& acdCallEvent, int32_t threadNo);

    /**
     * @brief SendOtherEvent        发送其他事件处理函数
     * @param acdCallEvent          坐席呼叫事件
     * @param threadNo              处理线程ID
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void SendOtherEvent(const OtherEventT& acdOtherEvent, int32_t threadNo);

    /**
     * @brief SendOtherEvent        发送路由事件处理函数
     * @param acdCallEvent          坐席呼叫事件
     * @param threadNo              处理线程ID
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void SendRouteEvent(const RouteEventT& acdRouteEvent, int32_t threadNo);

    /**
     * @brief SendOtherEvent        发送媒体事件处理函数
     * @param acdCallEvent          坐席呼叫事件
     * @param threadNo              处理线程ID
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void SendMediaEvent(const MediaEventT& acdMediaEvent, int32_t threadNo);

    /**
     * @brief GetHeartBeatTimeOut      获取心跳事件间隔
     * @return 心跳时间
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    int32_t GetHeartBeatTimeOut();

    /**
     * @brief AddAcdCallEvent :写呼叫事件进队列
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时08分14秒
     */
    bool AddAcdCallEvent(AgentEventT& event);

    /**
     * @brief AddAcdMediaEvent :写媒体事件进队列
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时08分27秒
     */
    bool AddAcdMediaEvent(MediaEventT& event);

    /**
     * @brief AddAcdRouteEvent :写路由事件进队列
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时08分37秒
     */
    bool AddAcdRouteEvent(RouteEventT& event);

    /**
     * @brief AddAcdOtherEvent :写其他事件进队列
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时08分47秒
     */
    bool AddAcdOtherEvent(OtherEventT& event);

    /**
     * @brief GetAcdCallEvent :从队列读取呼叫事件
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时08分59秒
     */
    bool GetAcdCallEvent(AgentEventT& event, const int32_t threadNo);

    /**
     * @brief GetAcdMediaEvent 从队列读取媒体事件
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时09分11秒
     */
    bool GetAcdMediaEvent(MediaEventT& event, const int32_t threadNo);

    /**
     * @brief GetAcdRouteEvent :从队列读取路由事件
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时09分22秒
     */
    bool GetAcdRouteEvent(RouteEventT& event, const int32_t threadNo);

    /**
     * @brief GetAcdOtherEvent :从队列读取其他事件
     *
     * @param event
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时09分36秒
     */
    bool GetAcdOtherEvent(OtherEventT& event, const int32_t threadNo);

    /**
     * @brief CreateAcdCBThread :创建处理回调消息线程
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时09分54秒
     */
    bool CreateAcdCBThread();

    /**
     * @brief CreateApListenThread     创建监听AP服务的处理线程
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool CreateApListenThread();

    /**
     * @brief IsQueueEmpty :判断事件队列是否为空
     *
     * @param threadNo
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时10分03秒
     */
    bool IsQueueEmpty(const int32_t& threadNo);

    /**
     * @brief HeartBeat :检测ap与ACD之间的心跳状态
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时10分20秒
     */
    void HeartBeat();

    /**
     * @brief Backup:倒换,当心跳异常时且满足条件,client改用备连接
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时10分45秒
     */
    bool Backup();

    /**
     * @brief Instance :返回全局唯一的AgentProxy实例
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时14分28秒
     */
    static AgentProxy* Instance() {
        static AgentProxy agentproxy;
        return &agentproxy;
    }

    /**
     * @brief Destroy 销毁资源
     * @see
     * @note
     * @date    2012年06月29日 13时18分58秒
     */
    void Destroy();
    /**
     * @brief CreateCheckHBThread :创建检查心跳消息线程
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 13时09分54秒
     */
    bool CreateCheckHBThread();

    /**
     * @brief IsNeedApThreadShutdown :杀掉线程
     *
     * @return
     * @see
     * @note
     * @date    2012年07月01日 15时26分48秒
     */
    bool IsNeedApThreadShutdown();

    /**
     * @brief CreateClient            创建连接ACD的客户端实例
     * @param Ip                      ACD的IP地址
     * @param Port                    ACD的端口
     * @param connectNum              连接ACD的连接数
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool CreateClient(std::string Ip, int32_t Port, int32_t connectNum);

    /**
     * @brief ClearHaveSendMsgNum 清空转发消息数
     *
     * @return
     * @see
     * @note
     * @date    2012年07月02日 14时08分36秒
     */
    void ClearHaveSendMsgNum();

    /**
     * @brief StartApListen            开始监听AP的服务
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool StartApListen();

    /**
     * @brief ClearTimeOutAgentInfo       清除已经signout但还存在信息的坐席,防止丢失signout事件
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void ClearTimeOutAgentInfo(std::string agentId);

    void ChangeAgentListIp(AgentInfoListT& agentInfoList);
    void ChangeAgentIp(AgentInfoT& agentInfo);


    /*衔接server和client的公共接口*/
public:

    AcdResultT SignIn(const std::string& agentId,
                      const std::string& agentDn, const std::string& agentPwd,
                      const StatusChangeT& statusChangetype, bool autoAnswer,
                      bool fcSignin, const std::string& skills,
                      int64_t& handle,
                      const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT SignOut(int64_t handle, const std::string& agentId,
                       const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT SetAgentStatus(int64_t handle, const std::string& agentId,
                              const AgentStatusT& agentStatus, const std::string& restReason,
                              const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetAgentStatus(int64_t handle, const std::string& agentId, AgentStatusT& agentStatus,
                              const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ResetStatuschangetype(int64_t handle, const std::string& agentId,
                                     const StatusChangeT& statusChangetype, const std::map<std::string, std::string> ctx,
                                     uint64_t time_rcv);
    AcdResultT ResetAutoAnswer(int64_t handle, const std::string& agentId, bool autoAnswer,
                               const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ResetSkill(int64_t handle, const std::string& agentId, const std::string& skill,
                          const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT Reset(int64_t handle, const std::string& agentId,
                     const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT OutboundCall(int64_t handle, const std::string& agentId, const std::string& callerId,
                            const std::string& destId, const std::string& forCallerDispNum, const std::string& forCalleeDispNum,
                            int32_t timeout, const CallModeT& callMode, const CallTypeT& callType,
                            const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT AnswerCall(int64_t handle, const std::string& agentId,
                          const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ReleaseCall(int64_t handle, const std::string& agentId,
                           const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT Hold(int64_t handle, const std::string& agentId,
                    const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT RetrieveHeld(int64_t handle, const std::string& agentId,
                            const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT Consult(int64_t handle, const std::string& agentId, const std::string& callerId,
                       const std::string& destId, const std::string& forCallerDispNum, const std::string& forCalleeDispNum,
                       const CallTypeT& callType, const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ConsultReconnect(int64_t handle, const std::string& agentId,
                                const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ConsultTransfer(int64_t handle, const std::string& agentId,
                               const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT SingleStepTransfer(int64_t handle, const std::string& agentId,
                                  const std::string& callerId, const std::string& destId, const std::string& forCallerDispNum,
                                  const std::string& forCalleeDispNum, bool isPassthrough, const CallTypeT& transferType,
                                  const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ConsultConference(int64_t handle, const std::string& agentId,
                                 const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ConferenceJoin(int64_t handle, const std::string& agentId, const std::string& callerId,
                              const std::string& destAgentId, const std::string& forCallerDispNum,
                              const std::string& forCalleeDispNum, const ConferenceT& conferenceType,
                              const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT SetAssociateData(int64_t handle, const std::string& agentId, const std::string& key,
                                const std::string& value, const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetAssociateData(int64_t handle, const std::string& agentId, const std::string& key,
                                std::string& value, const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ForceSignIn(int64_t handle,
                           const std::string& agentId, const std::string& destAgentId,
                           const std::string& agentDn, const std::string& agentPwd,
                           const StatusChangeT& statusChangetype, bool autoAnswer, bool fcSignin,
                           const std::string& skills, const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ForceSignOut(int64_t handle, const std::string& agentId, const std::string& destAgentId,
                            const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ForceSetAgentStatus(int64_t handle, const std::string& agentId,
                                   const std::string& destAgentId, const AgentStatusT& agentStatus,
                                   const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT Listen(int64_t handle, const std::string& agentId, const std::string& callerId,
                      const std::string& destAgentId, const std::string& forCallerDispNum,
                      const std::string& forCalleeDispNum, const std::map<std::string, std::string> ctx,
                      uint64_t time_rcv);
    AcdResultT StopListen(int64_t handle, const std::string& agentId, const std::string& destAgentId,
                          const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT Insert(int64_t handle, const std::string& agentId, const std::string& callerId,
                      const std::string& destAgentId, const std::string& forCallerDispNum,
                      const std::string& forCalleeDispNum, const std::map<std::string, std::string> ctx,
                      uint64_t time_rcv);
    AcdResultT StopInsert(int64_t handle, const std::string& agentId, const std::string& destAgentId,
                          const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT SwitchInsertorListen(int64_t handle, const std::string& agentId,
                                    const std::string& callerId, const std::string& destAgentId, const std::string& forCallerDispNum,
                                    const std::string& forCalleeDispNum, const std::map<std::string, std::string> ctx,
                                    uint64_t time_rcv);
    AcdResultT Break(int64_t handle, const std::string& agentId, const std::string& destAgentId,
                     const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT SendDTMF(int64_t handle, const std::string& agentId, const std::string& digitals,
                        const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT StartPlay(int64_t handle, const std::string& agentId, const std::string& filename,
                         const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT StopPlay(int64_t handle, const std::string& agentId,
                        const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT MuteOn(int64_t handle, const std::string& agentId,
                      const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT MuteOff(int64_t handle, const std::string& agentId,
                       const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetAgentDetailByAgentID(int64_t handle, const std::string& agentId,
                                       const std::string& destAgentId, AgentInfoT& agentInfo, const std::map<std::string, std::string> ctx,
                                       uint64_t time_rcv);
    AcdResultT GetAgentDetailByAgentDN(int64_t handle, const std::string& agentId,
                                       const std::string& destAgentDn, AgentInfoT& agentInfo, const std::map<std::string, std::string> ctx,
                                       uint64_t time_rcv);
    AcdResultT GetAgentDetailsByAgentIDs(int64_t handle, const std::string& agentId,
                                         const StringListT& destAgentIdList, AgentInfoListT& agentInfoList,
                                         const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetAgentDetailsByAgentDNs(int64_t handle, const std::string& agentId,
                                         const StringListT& destAgentDnList, AgentInfoListT& agentInfoList,
                                         const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetRecordFileName(int64_t handle, const std::string& agentId, std::string& filename,
                                 const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetRestReason(int64_t handle, const std::string& agentId, StringListT& restReason,
                             const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetSkill(int64_t handle, const std::string& agentId, StringListT& skill,
                        const std::map<std::string, std::string>& ctx, uint64_t time_rcv);
    AcdResultT GetAgentNumberBySkill(int64_t handle, const std::string& agentId,
                                     const std::string& skill, int32_t& agentNum, const std::map<std::string, std::string> ctx,
                                     uint64_t time_rcv);
    AcdResultT GetAgentDetailsBySkill(int64_t handle, const std::string& agentId,
                                      const std::string& skill, int32_t& agentNum, AgentInfoListT& agentInfoList,
                                      const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetSkillWaitingNumber(int64_t handle, const std::string& agentId,
                                     const std::string& skill, int32_t& queueNum, int32_t& freeNum,
                                     const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetSkillWaitingCallInfo(int64_t handle, const std::string& agentId,
                                       const std::string& skill, int32_t& queueNum, QueueInfoListT& queueInfoList,
                                       const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetPrivateQueue(int64_t handle, const std::string& agentId,
                               const std::string& destAgentId, int32_t& queueNum, QueueInfoListT& queueInfoList,
                               const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT GetSysInfo(int64_t handle, const std::string& agentId, SysInfoT& sysInfo,
                          const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT SynchronizeCTITime(int64_t handle, const std::string& agentId, int64_t& timestamp,
                                  const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT Heartbeat(int64_t handle, const std::string& agentId,
                         const std::map<std::string, std::string> ctx, uint64_t time_rcv);
    AcdResultT ResetConfig(const std::string& password, const std::map<std::string, std::string>& ctx,
                           uint64_t time_rcv);

    AcdResultT JumptheQueue(int64_t handle, const std::string& agentId, int64_t requestId,
                            const std::map<std::string, std::string>& ctx, uint64_t time_rcv);
    bool ReLoadConfig();
    bool GetAgents(ApAgentInfoListT& agentInfoList);
    AcdResultT GetCallInfo(int64_t handle, const std::string& agentId, 
                            int32_t type, const std::string& input, std::string& result,
                            const std::map<std::string, std::string>& ctx);


    /*私有成员接口声明*/
private:
    /**
    * @brief readConf :读取配置文件内容
    *
    * @return
    * @see
    * @note
    * @date    2013年03月25日
    */
    bool readConf(const char* conf_filepath);

    /**
     * @brief getApCommonConf       获取ap的通用配置
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool getApCommonConf(const char* conf_filepath);

    /**
     * @brief getAcdConf       获取ap的关于acd的连接信息配置
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool getAcdConf(const char* conf_filepath);

    /**
     * @brief getBgccConf       获取ap的关于bgcc的相关配置
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool getBgccConf(const char* conf_filepath);
    /**
     * @brief Init_log :初始化日志模块
     *
     * @return
     * @see
     * @note
     * @date    2012年06月28日 19时55分35秒
     */
    bool Init_log();

    /**
     * @brief SetApThreadShutdown      设置关闭线程标志位
     * @return
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void SetApThreadShutdown();

    /**
     * @brief GetCtiService 获取当前指向
     *
     * @return
     * @see
     * @note
     * @date    2012年07月09日 15时09分10秒
     */
    APCONNACDSTATE GetCtiService();

    /**
     * @brief SetCtiService 设置当前AP指向
     *
     * @param State
     *
     * @return
     * @see
     * @note
     * @date    2012年07月09日 15时09分24秒
     */
    void SetCtiService(APCONNACDSTATE State);

    /**
     * @brief SetApClient       重新设置连接ACD的客户端实例
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool SetApClient(ApClient* client);

    /**
     * @brief AddHeartBeatCount       心跳异常次数+1
     * @return
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void AddHeartBeatCount();

    /**
     * @brief ClearHeartBeatCount       清空心跳异常次数
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void ClearHeartBeatCount();

    /**
     * @brief GetHeartBeatCount       获取心跳异常次数
     * @return  异常心跳次数
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    int32_t GetHeartBeatCount();

    /**
     * @brief GetValidAcd       获取可用ACD
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool GetValidAcd();

    /**
     * @brief GetValidAcd       尝试连接ACD
     * @return  成功:true;失败:false
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    bool TryConnAcd(std::string strIp, int32_t Port, APCONNACDSTATE state);

    /**
     * @brief ReSignIn       连接ACD后进行坐席重签
     * @return
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    void ReSignIn(APCONNACDSTATE state);

    /**
     * @brief getProxyName       获取客户端连接的proxyname
     * @return  连接ID
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    std::string getProxyName(const std::map<std::string, std::string>& ctx);

    /**
     * @brief getProxyIP       获取客户端IP地址
     * @return
     * @see
     * @note
     * @date    2013年03月26日 21时23分25秒
     */
    std::string getProxyIP(const std::map<std::string, std::string>& ctx);

    /*私有成员变量声明*/
private:

    int32_t              _heartBeatCount;           /** 当前心跳数*/
    int32_t              _apClientHandle;           /** 当前proxy的连接句柄*/
    int32_t              _apListenPort;
    int32_t              _ACDPort;                  /** ACD的端口号*/
    int32_t              _apListenPortOwn;
    int32_t              _apHeartBeatTimeout;
    int32_t              _apHeartBeatMaxTrytimes;
    int32_t              _apWarnSendmsgTimeout;
    int32_t              _apServerThreadPoolNum;    /**bgcc服务的线程数**/
    int32_t              _apClientConnNum;          /**bgcc连接数,配置**/
    int32_t              _CallbackThreadNum;        /**接收回调事件线程数**/
    int32_t              _AcdMainPort;
    int32_t              _AcdBackupPort;
    int32_t              _AgentTimeOut;             /**超时的时间(用于删除未收到signout事件的坐席)**/

    ApServer*            _pApServer;                /** ApServer对象指针*/
    ApService*           _pApService;               /** ApService对象指针*/
    ApClient*            _pApClient;                /** ApClient对象指针*/
    ApEventQ*            _ApEventQ;                 /** 事件队列指针,初始化时赋值*/
    Thread*
    _apHBCheckThread;          /** 心跳检测智能指针数组(继承BGCC),检测主备ACD心跳*/
    Thread*              _apListenThread;           /** AP监听接口线程指针*/

    std::string          _apHost;
    std::string          _strMainACDIP;             /** 主ACD的IP地址*/
    std::string          _strBackACDIP;             /** 备ACD的IP地址*/
    APCONNACDSTATE       _ctiService;               /** 标示当前连的哪一台ACD*/
    MapAgentIdDataType   _mapAgentIdData;           /** 维护agentbar连接数据的hash_map*/
    std::vector<Thread*> _apCallbackThreadVec;
    ServiceManager       _serviceManager;
    volatile bool        _shutdown;

    Mutex                _mapMutex;                 /*map锁*/
    Mutex                _threadShutdownMutex;
    Mutex                _ctiServiceMutex ;
    Mutex                _HBCountMutex;
    Mutex                _ApClientMutex;            /** proxy锁*/
private:
    AgentProxy() {}
    ~AgentProxy() {}

};

#endif // AGENTPROXY