Plugin Directory

Changeset 1888627


Ignore:
Timestamp:
06/07/2018 08:39:32 AM (8 years ago)
Author:
gosomi
Message:

2.0.6 적용 및 다른 결제 수단 사용 가능하도록 업데이트

Location:
woo-bootpay/trunk
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • woo-bootpay/trunk/bootpay-woocommerce.php

    r1858733 r1888627  
    44 * Plugin URI: https://www.bootpay.co.kr
    55 * Description: 우커머스에 PG를 손쉽게 붙일 수 연동 플러그인 ( 이니시스 / 다날 / KCP / LGU+ 모두 쉽게 붙이는 Woo-bootpay )
    6  * Version: 1.1.10
     6 * Version: 1.1.11
    77 * Author: Gosomi
    88 * Author URI: https://blog.areum.io
     
    1010 */
    1111
    12 require_once( 'bootpay-api.php' );
    13 
    14 add_action( 'init', function() {
    15     register_post_status( 'wc-wating-bank', [
    16         'label'                     => __( '입금대기', 'bootpay-with-woocommerce' ),
    17         'label_count'               => _n_noop( '입금대기 <span class="count">(%s)</span>', '입금대기 <span class="count">(%s)</span>' ),
    18         'show_in_admin_all_list'    => true,
    19         'public'                    => true,
    20         'show_in_admin_status_list' => true,
    21         'exclude_from_search'       => false
    22     ] );
    23 } );
    24 add_action( 'wc_order_statuses', function( $order_statuses ) {
    25     $order_statuses['wc-wating-bank'] = __( '입금대기', 'bootpay-with-woocommerce' );
    26 
    27     return $order_statuses;
    28 } );
    29 add_filter( 'woocommerce_payment_gateways', function() {
    30     $methods[] = 'WC_Gateway_Bootpay';
    31 
    32     return $methods;
    33 } );
    34 
    35 add_action( 'plugins_loaded', 'init_bootpay_plugin', 0 );
    36 load_plugin_textdomain( 'bootpay-with-woocommerce', false, dirname( plugin_basename( __FILE__ ) ) . '/languages' );
    37 
    38 function init_bootpay_plugin() {
    39     if( ! class_exists( 'WC_Payment_Gateway' ) || class_exists( 'WC_Gateway_Bootpay' ) ) {
    40         return;
    41     }
    42 
    43     class WC_Gateway_Bootpay extends WC_Payment_Gateway {
    44 
    45         const CURRENT_VERSION    = '1.1.3';
    46         const BOOTPAY_WC_DOMAIN  = 'bootpay-with-woocommerce';
    47         const SUPPORT_CURRENCY   = ['KRW'];
    48         const PAYMENT_SUBMIT     = 'BOOTPAY_PAYMENT_SUBMIT';
    49         const VBANK_NOTIFICATION = 'BOOTPAY_VBANK_NOTI';
    50 
    51         static $loadActions = false;
    52 
    53         public function __construct() {
    54             $this->id                 = 'bootpay_gateway';
    55             $this->method_title       = __( '부트페이', self::BOOTPAY_WC_DOMAIN );
    56             $this->method_description = __( '* 부트페이를 이용하여 결제를 할 수 있습니다.', self::BOOTPAY_WC_DOMAIN );
    57             $this->has_fields         = true;
    58             $this->supports           = ['products', 'refunds'];
    59             $this->enabled            = $this->is_valid_currency();
    60 
    61             $this->init_form_fields();
    62             $this->init_settings();
    63 
    64             $this->title       = $this->get_option( 'title' );
    65             $this->description = $this->get_option( 'description' );
    66             if( !static::$loadActions ) {
    67                 $this->load_actions();
    68             }
    69 
    70         }
    71 
    72         public function init_form_fields() {
    73             $this->form_fields = [
    74                 'enabled'      => [
    75                     'title'   => __( 'Enable/Disable', 'woocommerce' ),
    76                     'type'    => 'checkbox',
    77                     'label'   => __( '부트페이 결제 활성화', self::BOOTPAY_WC_DOMAIN ),
    78                     'default' => 'yes'
    79                 ],
    80                 'title'        => [
    81                     'title'       => __( 'Title', 'woocommerce' ),
    82                     'type'        => 'text',
    83                     'description' => __( '결제 정보 수단 이름', self::BOOTPAY_WC_DOMAIN ),
    84                     'default'     => __( '부트페이 [ 휴대폰 소액결제 / 카드 결제 ]', self::BOOTPAY_WC_DOMAIN ),
    85                     'desc_tip'    => true
    86                 ],
    87                 'description'  => [
    88                     'title'       => __( 'Customer Message', 'woocommerce' ),
    89                     'type'        => 'textarea',
    90                     'description' => __( '구매 고객에게 결제 정보에 대한 설명을 보여줍니다.', self::BOOTPAY_WC_DOMAIN ),
    91                     'default'     => __( '주문확정 버튼을 누르면 결제를 진행할 수 있습니다.', self::BOOTPAY_WC_DOMAIN )
    92                 ],
    93                 'notification' => [
    94                     'title'             => __( '가상계좌 입금 통지 URL', self::BOOTPAY_WC_DOMAIN ),
    95                     'type'              => 'text',
    96                     'custom_attributes' => ['readonly' => 'true'],
    97                     'description'       => __( 'URL을 복사 한 후 부트페이 관리자에서 결제연동 > Private key관리 > 웹 ( FeedbackUrl )에 붙여넣기 한 후 저장해주세요.', self::BOOTPAY_WC_DOMAIN ),
    98                     'placeholder'       => add_query_arg( 'wc-api', self::VBANK_NOTIFICATION, site_url() ),
    99                     'default'           => add_query_arg( 'wc-api', self::VBANK_NOTIFICATION, site_url() )
    100                 ],
    101                 'js_api_key'   => [
    102                     'title'       => __( 'Javascript API KEY', self::BOOTPAY_WC_DOMAIN ),
    103                     'type'        => 'text',
    104                     'description' => __( '부트페이 관리자에서 자바스크립트 API KEY를 복사한 후 붙여넣기 해주세요.', self::BOOTPAY_WC_DOMAIN ),
    105                     'placeholder' => __( '자바스크립트 API KEY를 입력해주세요.', self::BOOTPAY_WC_DOMAIN )
    106                 ],
    107                 'rest_api_key' => [
    108                     'title'       => __( 'REST API KEY', self::BOOTPAY_WC_DOMAIN ),
    109                     'type'        => 'text',
    110                     'description' => __( '부트페이 관리자에서 REST API KEY를 복사한 후 붙여넣기 해주세요. 결제 취소 / 검증 시에 반드시 필요합니다.', self::BOOTPAY_WC_DOMAIN ),
    111                     'placeholder' => __( 'REST API KEY를 입력해주세요.', self::BOOTPAY_WC_DOMAIN )
    112                 ],
    113                 'private_key'  => [
    114                     'title'       => __( 'PRIVATE KEY', self::BOOTPAY_WC_DOMAIN ),
    115                     'type'        => 'text',
    116                     'description' => __( '서버 인증에 필요한 PRIVATE KEY를 관리자에서 복사한 후 붙여넣기 해주세요.', self::BOOTPAY_WC_DOMAIN ),
    117                     'placeholder' => __( 'PRIVATE KEY를 입력해주세요.', self::BOOTPAY_WC_DOMAIN )
    118                 ],
    119                 'agree_window' => [
    120                     'title'       => __( '동의창 보이기 여부', self::BOOTPAY_WC_DOMAIN ),
    121                     'type'        => 'checkbox',
    122                     'description' => __( '부트페이 약관 동의창을 보이게 하려면 체크해주세요.', self::BOOTPAY_WC_DOMAIN )
    123                 ]
    124             ];
    125         }
    126 
    127         /**
    128          * 지원하는 결제 리스트
    129          * @return bool
    130          */
    131         public function is_valid_currency() {
    132             if( ! in_array( get_woocommerce_currency(), self::SUPPORT_CURRENCY ) ) {
    133                 $this->msg = sprintf( "부트페이는 %s 화폐 결제를 지원하지 않습니다.", get_woocommerce_currency() );
    134 
    135                 return false;
    136             }
    137 
    138             return true;
    139         }
    140 
    141         /**
    142          * admin option 호출
    143          * 관리자 환경설정에서 option 및 타이틀 기능을 커스텀 한다.
    144          */
    145         public function admin_options() {
    146             $this->renderFile( 'header.php', [
    147                 'title' => __( '부트페이 설정', self::BOOTPAY_WC_DOMAIN )
    148             ] );
    149         }
    150 
    151         /**
    152          * Action Gateway를 호출하여 Override한다.
    153          */
    154         public function load_actions() {
    155             add_filter( 'login_redirect', [$this, 'bootpay_login_redirect'], 30, 3 );
    156             add_action( 'woocommerce_api_' . strtolower( self::PAYMENT_SUBMIT ), [$this, 'payment_validation'] );
    157             add_action( 'woocommerce_api_' . strtolower( self::VBANK_NOTIFICATION ), [$this, 'vbank_notification'] );
    158             add_action( 'woocommerce_order_details_after_order_table', [$this, 'bootpay_order_table'], 10, 1 );
    159             add_action( "woocommerce_update_options_payment_gateways_{$this->id}", [$this, 'process_admin_options'] );
    160             add_action( "wp_ajax_bootpay_payment_response", [$this, 'pre_bootpay_payment_response'] );
    161             add_action( "admin_enqueue_scripts", [$this, 'enqueue_inject_admin_bootpay_script'], 10000 );
    162             add_action( "wp_enqueue_scripts", [$this, 'enqueue_inject_bootpay_script'], 10000 );
    163             add_filter( 'wc_checkout_params', [$this, 'inject_checkout_params'] );
    164             add_action( 'wp_head', [$this, 'insert_meta_tag'] );
    165             wp_register_script( 'bootpay-script', plugins_url( '/assets/js/bootpay.js', plugin_basename( __FILE__ ) ) );
    166             wp_register_script( 'bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js" );
    167             wp_enqueue_script( 'jquery' );
    168             wp_enqueue_script( 'bootpay-script' );
    169             wp_enqueue_script( 'bootpay-cdn-script' );
    170             if( is_product() ) {
    171                 wp_register_script( 'bootpay-analystics-script', plugins_url( '/assets/js/bootpay-analystics.js', plugin_basename( __FILE__ ) ) );
    172                 wp_enqueue_script( 'bootpay-analystics-script' );
    173             }
    174             static::$loadActions = true;
    175         }
    176 
    177         public function insert_meta_tag() {
    178             echo "\t<meta name='bootpay-application-id' content='{$this->get_option('js_api_key')}' />\n";
    179         }
    180 
    181         public function bootpay_order_table( $order ) {
    182             return $this->renderFile( 'order_detail.php', [
    183                 'pg_name'     => $order->get_meta( 'bootpay_pg_name' ),
    184                 'method_name' => $order->get_meta( 'bootpay_method_name' ),
    185                 'bankname'    => $order->get_meta( 'bootpay_bankname' ),
    186                 'holder'      => $order->get_meta( 'bootpay_holder' ),
    187                 'account'     => $order->get_meta( 'bootpay_account' ),
    188                 'username'    => $order->get_meta( 'bootpay_username' ),
    189                 'expire'      => $order->get_meta( 'bootpay_expire' ),
    190                 'price'       => number_format( (int) $order->get_total() )
    191             ] );
    192         }
    193 
    194         public function pre_bootpay_payment_response() {
    195             if( ! empty( $_POST['order_key'] ) ) {
    196                 $order_id = wc_get_order_id_by_order_key( $_POST['order_key'] );
    197                 $this->renderJson( $this->bootpay_payment_response( $order_id ) );
    198             } else {
    199                 $this->renderJson( [
    200                     'result'   => 'failure',
    201                     'messages' => __( '해당되는 Order Key 정보를 찾지 못했습니다.', self::BOOTPAY_WC_DOMAIN )
    202                 ] );
    203             }
    204         }
    205 
    206         /**
    207          * Bootpay로 주문한 데이터 결과를 가져온다.
    208          */
    209         public function bootpay_payment_response( $order_id ) {
    210             $order        = new WC_Order( $order_id );
    211             $checkout_url = $order->has_status( [
    212                 'processing',
    213                 'completed'
    214             ] ) ? $order->get_checkout_order_received_url() : $order->get_checkout_payment_url( false );
    215             $order_items  = $order->get_items();
    216             if( is_array( $order_items ) ) {
    217                 $items = [];
    218                 foreach( $order_items as $item_id => $item ) {
    219                     $cats  = [];
    220                     $terms = get_the_terms( $item['product_id'], 'product_cat' );
    221                     foreach( $terms as $term ) {
    222                         $cats[] = $term->slug;
    223                     }
    224                     $line_price = wc_get_order_item_meta( $item_id, '_line_total', true );
    225                     array_push( $items, [
    226                         'item_name' => $item['name'],
    227                         'qty'       => $item['qty'],
    228                         'unique'    => (string) $item_id,
    229                         'price'     => (int) ( $line_price / $item['qty'] ),
    230                         'cat1'      => empty( $cats[0] ) ? '' : $cats[0],
    231                         'cat2'      => empty( $cats[1] ) ? '' : $cats[1],
    232                         'cat3'      => empty( $cats[2] ) ? '' : $cats[2],
    233                     ] );
    234                 }
    235             }
    236 
    237             $order_data = [
    238                 'name'      => sizeof( $items ) > 1 ? sprintf( "%s 외 %s 개", $items[0]['item_name'], sizeof( $items ) - 1 ) : $items[0]['item_name'],
    239                 'price'     => $order->get_total(),
    240                 'items'     => $items,
    241                 'order_id'  => $order_id,
    242                 'user_info' => [
    243                     'username' => $order->billing_last_name . $order->billing_first_name,
    244                     'phone'    => ( empty( $order->get_billing_phone() ) ? '010-0000-0000' : $order->get_billing_phone() ),
    245                     'email'    => $order->billing_email,
    246                     'addr'     => strip_tags( implode( ' ', [
    247                         $order->get_billing_city(),
    248                         $order->get_billing_address_1(),
    249                         $order->get_billing_address_2()
    250                     ] ) )
    251                 ]
    252             ];
    253 
    254             return [
    255                 'result'       => 'success',
    256                 'order_key'    => $order->order_key,
    257                 'order_id'     => $order_id,
    258                 'order_data'   => $order_data,
    259                 'checkout_url' => add_query_arg( [
    260                     'wc-api'   => self::PAYMENT_SUBMIT,
    261                     'order_id' => $order_id
    262                 ], $checkout_url ),
    263             ];
    264         }
    265 
    266         /**
    267          * Bootpay Script 추가
    268          */
    269         public function enqueue_inject_bootpay_script() {
    270             wp_register_script( 'bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js" );
    271             wp_register_script( 'bootpay-script', plugins_url( '/assets/js/bootpay.js', plugin_basename( __FILE__ ) ) );
    272             wp_register_script( 'bootpay-order-script', plugins_url( '/assets/js/bootpay-order.js', plugin_basename( __FILE__ ) ) );
    273             // 일단 주석 checkout을 주석처리할 경우 woocommerce의 wc_checkout_params의 값을 사용 못함
     12require_once('bootpay-api.php');
     13
     14add_action('init', function () {
     15    register_post_status('wc-wating-bank', [
     16        'label' => __('입금대기', 'bootpay-with-woocommerce'),
     17        'label_count' => _n_noop('입금대기 <span class="count">(%s)</span>', '입금대기 <span class="count">(%s)</span>'),
     18        'show_in_admin_all_list' => true,
     19        'public' => true,
     20        'show_in_admin_status_list' => true,
     21        'exclude_from_search' => false
     22    ]);
     23});
     24add_action('wc_order_statuses', function ($order_statuses) {
     25    $order_statuses['wc-wating-bank'] = __('입금대기', 'bootpay-with-woocommerce');
     26
     27    return $order_statuses;
     28});
     29add_filter('woocommerce_payment_gateways', function ($methods) {
     30    $methods[] = 'WC_Gateway_Bootpay';
     31    return $methods;
     32});
     33
     34add_action('plugins_loaded', 'init_bootpay_plugin', 0);
     35load_plugin_textdomain('bootpay-with-woocommerce', false, dirname(plugin_basename(__FILE__)) . '/languages');
     36
     37function init_bootpay_plugin()
     38{
     39    if (!class_exists('WC_Payment_Gateway') || class_exists('WC_Gateway_Bootpay')) {
     40        return;
     41    }
     42
     43    class WC_Gateway_Bootpay extends WC_Payment_Gateway
     44    {
     45
     46        const CURRENT_VERSION = '2.0.6';
     47        const BOOTPAY_WC_DOMAIN = 'bootpay-with-woocommerce';
     48        const SUPPORT_CURRENCY = ['KRW'];
     49        const PAYMENT_SUBMIT = 'BOOTPAY_PAYMENT_SUBMIT';
     50        const VBANK_NOTIFICATION = 'BOOTPAY_VBANK_NOTI';
     51
     52        static $loadActions = false;
     53
     54        public function __construct()
     55        {
     56            $this->id = 'bootpay_gateway';
     57            $this->method_title = __('부트페이', self::BOOTPAY_WC_DOMAIN);
     58            $this->method_description = __('* 부트페이를 이용하여 결제를 할 수 있습니다.', self::BOOTPAY_WC_DOMAIN);
     59            $this->has_fields = true;
     60            $this->supports = ['products', 'refunds'];
     61            $this->enabled = $this->is_valid_currency();
     62
     63            $this->init_form_fields();
     64            $this->init_settings();
     65
     66            $this->title = $this->get_option('title');
     67            $this->description = $this->get_option('description');
     68            if (!static::$loadActions) {
     69                $this->load_actions();
     70            }
     71
     72        }
     73
     74        public function init_form_fields()
     75        {
     76            $this->form_fields = [
     77                'enabled' => [
     78                    'title' => __('Enable/Disable', 'woocommerce'),
     79                    'type' => 'checkbox',
     80                    'label' => __('부트페이 결제 활성화', self::BOOTPAY_WC_DOMAIN),
     81                    'default' => 'yes'
     82                ],
     83                'title' => [
     84                    'title' => __('Title', 'woocommerce'),
     85                    'type' => 'text',
     86                    'description' => __('결제 정보 수단 이름', self::BOOTPAY_WC_DOMAIN),
     87                    'default' => __('부트페이 [ 휴대폰 소액결제 / 카드 결제 ]', self::BOOTPAY_WC_DOMAIN),
     88                    'desc_tip' => true
     89                ],
     90                'description' => [
     91                    'title' => __('Customer Message', 'woocommerce'),
     92                    'type' => 'textarea',
     93                    'description' => __('구매 고객에게 결제 정보에 대한 설명을 보여줍니다.', self::BOOTPAY_WC_DOMAIN),
     94                    'default' => __('주문확정 버튼을 누르면 결제를 진행할 수 있습니다.', self::BOOTPAY_WC_DOMAIN)
     95                ],
     96                'notification' => [
     97                    'title' => __('가상계좌 입금 통지 URL', self::BOOTPAY_WC_DOMAIN),
     98                    'type' => 'text',
     99                    'custom_attributes' => ['readonly' => 'true'],
     100                    'description' => __('URL을 복사 한 후 부트페이 관리자에서 결제연동 > Private key관리 > 웹 ( FeedbackUrl )에 붙여넣기 한 후 저장해주세요.', self::BOOTPAY_WC_DOMAIN),
     101                    'placeholder' => add_query_arg('wc-api', self::VBANK_NOTIFICATION, site_url()),
     102                    'default' => add_query_arg('wc-api', self::VBANK_NOTIFICATION, site_url())
     103                ],
     104                'js_api_key' => [
     105                    'title' => __('Javascript API KEY', self::BOOTPAY_WC_DOMAIN),
     106                    'type' => 'text',
     107                    'description' => __('부트페이 관리자에서 자바스크립트 API KEY를 복사한 후 붙여넣기 해주세요.', self::BOOTPAY_WC_DOMAIN),
     108                    'placeholder' => __('자바스크립트 API KEY를 입력해주세요.', self::BOOTPAY_WC_DOMAIN)
     109                ],
     110                'rest_api_key' => [
     111                    'title' => __('REST API KEY', self::BOOTPAY_WC_DOMAIN),
     112                    'type' => 'text',
     113                    'description' => __('부트페이 관리자에서 REST API KEY를 복사한 후 붙여넣기 해주세요. 결제 취소 / 검증 시에 반드시 필요합니다.', self::BOOTPAY_WC_DOMAIN),
     114                    'placeholder' => __('REST API KEY를 입력해주세요.', self::BOOTPAY_WC_DOMAIN)
     115                ],
     116                'private_key' => [
     117                    'title' => __('PRIVATE KEY', self::BOOTPAY_WC_DOMAIN),
     118                    'type' => 'text',
     119                    'description' => __('서버 인증에 필요한 PRIVATE KEY를 관리자에서 복사한 후 붙여넣기 해주세요.', self::BOOTPAY_WC_DOMAIN),
     120                    'placeholder' => __('PRIVATE KEY를 입력해주세요.', self::BOOTPAY_WC_DOMAIN)
     121                ],
     122                'agree_window' => [
     123                    'title' => __('동의창 보이기 여부', self::BOOTPAY_WC_DOMAIN),
     124                    'type' => 'checkbox',
     125                    'description' => __('부트페이 약관 동의창을 보이게 하려면 체크해주세요.', self::BOOTPAY_WC_DOMAIN)
     126                ]
     127            ];
     128        }
     129
     130        /**
     131         * 지원하는 결제 리스트
     132         * @return bool
     133         */
     134        public function is_valid_currency()
     135        {
     136            if (!in_array(get_woocommerce_currency(), self::SUPPORT_CURRENCY)) {
     137                $this->msg = sprintf("부트페이는 %s 화폐 결제를 지원하지 않습니다.", get_woocommerce_currency());
     138
     139                return false;
     140            }
     141
     142            return true;
     143        }
     144
     145        /**
     146         * admin option 호출
     147         * 관리자 환경설정에서 option 및 타이틀 기능을 커스텀 한다.
     148         */
     149        public function admin_options()
     150        {
     151            $this->renderFile('header.php', [
     152                'title' => __('부트페이 설정', self::BOOTPAY_WC_DOMAIN)
     153            ]);
     154        }
     155
     156        /**
     157         * Action Gateway를 호출하여 Override한다.
     158         */
     159        public function load_actions()
     160        {
     161            add_filter('login_redirect', [$this, 'bootpay_login_redirect'], 30, 3);
     162            add_action('woocommerce_api_' . strtolower(self::PAYMENT_SUBMIT), [$this, 'payment_validation']);
     163            add_action('woocommerce_api_' . strtolower(self::VBANK_NOTIFICATION), [$this, 'vbank_notification']);
     164            add_action('woocommerce_order_details_after_order_table', [$this, 'bootpay_order_table'], 10, 1);
     165            add_action("woocommerce_update_options_payment_gateways_{$this->id}", [$this, 'process_admin_options']);
     166            add_action("wp_ajax_bootpay_payment_response", [$this, 'pre_bootpay_payment_response']);
     167            add_action("admin_enqueue_scripts", [$this, 'enqueue_inject_admin_bootpay_script'], 10000);
     168            add_action("wp_enqueue_scripts", [$this, 'enqueue_inject_bootpay_script'], 10000);
     169            add_filter('wc_checkout_params', [$this, 'inject_checkout_params']);
     170            add_action('wp_head', [$this, 'insert_meta_tag']);
     171            wp_register_script('bootpay-script', plugins_url('/assets/js/bootpay.js', plugin_basename(__FILE__)));
     172            wp_register_script('bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js");
     173            wp_enqueue_script('jquery');
     174            wp_enqueue_script('bootpay-script');
     175            wp_enqueue_script('bootpay-cdn-script');
     176            if (is_product()) {
     177                wp_register_script('bootpay-analystics-script', plugins_url('/assets/js/bootpay-analystics.js', plugin_basename(__FILE__)));
     178                wp_enqueue_script('bootpay-analystics-script');
     179            }
     180            static::$loadActions = true;
     181        }
     182
     183        public function insert_meta_tag()
     184        {
     185            echo "\t<meta name='bootpay-application-id' content='{$this->get_option('js_api_key')}' />\n";
     186        }
     187
     188        public function bootpay_order_table($order)
     189        {
     190            return $this->renderFile('order_detail.php', [
     191                'pg_name' => $order->get_meta('bootpay_pg_name'),
     192                'method_name' => $order->get_meta('bootpay_method_name'),
     193                'bankname' => $order->get_meta('bootpay_bankname'),
     194                'holder' => $order->get_meta('bootpay_holder'),
     195                'account' => $order->get_meta('bootpay_account'),
     196                'username' => $order->get_meta('bootpay_username'),
     197                'expire' => $order->get_meta('bootpay_expire'),
     198                'price' => number_format((int)$order->get_total())
     199            ]);
     200        }
     201
     202        public function pre_bootpay_payment_response()
     203        {
     204            if (!empty($_POST['order_key'])) {
     205                $order_id = wc_get_order_id_by_order_key($_POST['order_key']);
     206                $this->renderJson($this->bootpay_payment_response($order_id));
     207            } else {
     208                $this->renderJson([
     209                    'result' => 'failure',
     210                    'messages' => __('해당되는 Order Key 정보를 찾지 못했습니다.', self::BOOTPAY_WC_DOMAIN)
     211                ]);
     212            }
     213        }
     214
     215        /**
     216         * Bootpay로 주문한 데이터 결과를 가져온다.
     217         */
     218        public function bootpay_payment_response($order_id)
     219        {
     220            $order = new WC_Order($order_id);
     221            $checkout_url = $order->has_status([
     222                'processing',
     223                'completed'
     224            ]) ? $order->get_checkout_order_received_url() : $order->get_checkout_payment_url(false);
     225            $order_items = $order->get_items();
     226            if (is_array($order_items)) {
     227                $items = [];
     228                foreach ($order_items as $item_id => $item) {
     229                    $cats = [];
     230                    $terms = get_the_terms($item['product_id'], 'product_cat');
     231                    foreach ($terms as $term) {
     232                        $cats[] = $term->slug;
     233                    }
     234                    $line_price = wc_get_order_item_meta($item_id, '_line_total', true);
     235                    array_push($items, [
     236                        'item_name' => $item['name'],
     237                        'qty' => $item['qty'],
     238                        'unique' => (string)$item_id,
     239                        'price' => (int)($line_price / $item['qty']),
     240                        'cat1' => empty($cats[0]) ? '' : $cats[0],
     241                        'cat2' => empty($cats[1]) ? '' : $cats[1],
     242                        'cat3' => empty($cats[2]) ? '' : $cats[2],
     243                    ]);
     244                }
     245            }
     246
     247            $order_data = [
     248                'name' => sizeof($items) > 1 ? sprintf("%s 외 %s 개", $items[0]['item_name'], sizeof($items) - 1) : $items[0]['item_name'],
     249                'price' => $order->get_total(),
     250                'items' => $items,
     251                'order_id' => $order_id,
     252                'user_info' => [
     253                    'username' => $order->billing_last_name . $order->billing_first_name,
     254                    'phone' => (empty($order->get_billing_phone()) ? '010-0000-0000' : $order->get_billing_phone()),
     255                    'email' => $order->billing_email,
     256                    'addr' => strip_tags(implode(' ', [
     257                        $order->get_billing_city(),
     258                        $order->get_billing_address_1(),
     259                        $order->get_billing_address_2()
     260                    ]))
     261                ]
     262            ];
     263
     264            return [
     265                'result' => 'success',
     266                'order_key' => $order->order_key,
     267                'order_id' => $order_id,
     268                'order_data' => $order_data,
     269                'checkout_url' => add_query_arg([
     270                    'wc-api' => self::PAYMENT_SUBMIT,
     271                    'order_id' => $order_id
     272                ], $checkout_url),
     273            ];
     274        }
     275
     276        /**
     277         * Bootpay Script 추가
     278         */
     279        public function enqueue_inject_bootpay_script()
     280        {
     281            wp_register_script('bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js");
     282            wp_register_script('bootpay-script', plugins_url('/assets/js/bootpay.js', plugin_basename(__FILE__)));
     283            wp_register_script('bootpay-order-script', plugins_url('/assets/js/bootpay-order.js', plugin_basename(__FILE__)));
     284            // 일단 주석 checkout을 주석처리할 경우 woocommerce의 wc_checkout_params의 값을 사용 못함
    274285//          wp_dequeue_script( 'wc-checkout' );
    275             wp_enqueue_script( 'bootpay-script' );
    276             wp_enqueue_script( 'bootpay-order-script' );
    277             wp_enqueue_script( 'bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js", ['boot-app-id' => $this->get_option( 'js_app_key' )] );
    278         }
    279 
    280         /**
    281          *
    282          */
    283         public function enqueue_inject_admin_bootpay_script() {
    284             wp_register_script( 'bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js" );
    285             wp_register_script( 'bootpay-script', plugins_url( '/assets/js/bootpay.js', plugin_basename( __FILE__ ) ) );
    286             wp_register_script( 'bootpay-admin-script', plugins_url( '/assets/js/bootpay-admin.js', plugin_basename( __FILE__ ) ) );
    287             wp_enqueue_script( 'bootpay-script' );
    288             wp_enqueue_script( 'bootpay-admin-script' );
    289             wp_enqueue_script( 'bootpay-cdn-script' );
    290         }
    291 
    292         /**
    293          * 결제 요청시에 wc_checkout_params 값에 추가적인 field
    294          *
    295          * @param $params
    296          *
    297          * @return array
    298          */
    299         public function inject_checkout_params( $params ) {
    300             $params['js_api_key']        = $this->get_option( 'js_api_key' );
    301             $params['show_agree_window'] = $this->get_option( 'agree_window' );
    302 
    303             return $params;
    304         }
    305 
    306         public function process_payment( $order_id ) {
    307             $order        = new WC_Order( $order_id );
    308             $checkout_url = $order->has_status( [
    309                 'processing',
    310                 'completed'
    311             ] ) ? $order->get_checkout_order_received_url() : $order->get_checkout_payment_url( false );
    312             $order_items  = $order->get_items();
    313             if( is_array( $order_items ) ) {
    314                 $items = [];
    315                 foreach( $order_items as $item_id => $item ) {
    316                     $cats  = [];
    317                     $terms = get_the_terms( $item['product_id'], 'product_cat' );
    318                     foreach( $terms as $term ) {
    319                         $cats[] = $term->slug;
    320                     }
    321                     $line_price = wc_get_order_item_meta( $item_id, '_line_total', true );
    322                     array_push( $items, [
    323                         'item_name' => $item['name'],
    324                         'qty'       => $item['qty'],
    325                         'unique'    => (string) $item_id,
    326                         'price'     => (int) ( $line_price / $item['qty'] ),
    327                         'cat1'      => empty( $cats[0] ) ? '' : $cats[0],
    328                         'cat2'      => empty( $cats[1] ) ? '' : $cats[1],
    329                         'cat3'      => empty( $cats[2] ) ? '' : $cats[2],
    330                     ] );
    331                 }
    332             }
    333             $order_data = [
    334                 'name'      => sizeof( $items ) > 1 ? sprintf( "%s 외 %s 개", $items[0]['item_name'], sizeof( $items ) - 1 ) : $items[0]['item_name'],
    335                 'price'     => $order->get_total(),
    336                 'items'     => $items,
    337                 'order_id'  => $order_id,
    338                 'user_info' => [
    339                     'username' => $order->billing_last_name . $order->billing_first_name,
    340                     'phone'    => ( empty( $order->get_billing_phone() ) ? '010-0000-0000' : $order->get_billing_phone() ),
    341                     'email'    => $order->billing_email,
    342                     'addr'     => strip_tags( implode( ' ', [
    343                         $order->get_billing_city(),
    344                         $order->get_billing_address_1(),
    345                         $order->get_billing_address_2()
    346                     ] ) )
    347                 ]
    348             ];
    349 
    350             return [
    351                 'result'       => 'success',
    352                 'order_key'    => $order->order_key,
    353                 'order_id'     => $order_id,
    354                 'order_data'   => $order_data,
    355                 'checkout_url' => add_query_arg( [
    356                     'wc-api'   => self::PAYMENT_SUBMIT,
    357                     'order_id' => $order_id
    358                 ], $checkout_url ),
    359             ];
    360         }
    361 
    362         public function bootpay_login_redirect( $redirect_to, $request, $user ) {
     286            wp_enqueue_script('bootpay-script');
     287            wp_enqueue_script('bootpay-order-script');
     288            wp_enqueue_script('bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js", ['boot-app-id' => $this->get_option('js_app_key')]);
     289        }
     290
     291        /**
     292         *
     293         */
     294        public function enqueue_inject_admin_bootpay_script()
     295        {
     296            wp_register_script('bootpay-cdn-script', "https://cdn.bootpay.co.kr/js/bootpay-{$this->currentVersion()}.min.js");
     297            wp_register_script('bootpay-script', plugins_url('/assets/js/bootpay.js', plugin_basename(__FILE__)));
     298            wp_register_script('bootpay-admin-script', plugins_url('/assets/js/bootpay-admin.js', plugin_basename(__FILE__)));
     299            wp_enqueue_script('bootpay-script');
     300            wp_enqueue_script('bootpay-admin-script');
     301            wp_enqueue_script('bootpay-cdn-script');
     302        }
     303
     304        /**
     305         * 결제 요청시에 wc_checkout_params 값에 추가적인 field
     306         *
     307         * @param $params
     308         *
     309         * @return array
     310         */
     311        public function inject_checkout_params($params)
     312        {
     313            $params['js_api_key'] = $this->get_option('js_api_key');
     314            $params['show_agree_window'] = $this->get_option('agree_window');
     315
     316            return $params;
     317        }
     318
     319        public function process_payment($order_id)
     320        {
     321            $order = new WC_Order($order_id);
     322            $checkout_url = $order->has_status([
     323                'processing',
     324                'completed'
     325            ]) ? $order->get_checkout_order_received_url() : $order->get_checkout_payment_url(false);
     326            $order_items = $order->get_items();
     327            if (is_array($order_items)) {
     328                $items = [];
     329                foreach ($order_items as $item_id => $item) {
     330                    $cats = [];
     331                    $terms = get_the_terms($item['product_id'], 'product_cat');
     332                    foreach ($terms as $term) {
     333                        $cats[] = $term->slug;
     334                    }
     335                    $line_price = wc_get_order_item_meta($item_id, '_line_total', true);
     336                    array_push($items, [
     337                        'item_name' => $item['name'],
     338                        'qty' => $item['qty'],
     339                        'unique' => (string)$item_id,
     340                        'price' => (int)($line_price / $item['qty']),
     341                        'cat1' => empty($cats[0]) ? '' : $cats[0],
     342                        'cat2' => empty($cats[1]) ? '' : $cats[1],
     343                        'cat3' => empty($cats[2]) ? '' : $cats[2],
     344                    ]);
     345                }
     346            }
     347            $order_data = [
     348                'name' => sizeof($items) > 1 ? sprintf("%s 외 %s 개", $items[0]['item_name'], sizeof($items) - 1) : $items[0]['item_name'],
     349                'price' => $order->get_total(),
     350                'items' => $items,
     351                'order_id' => $order_id,
     352                'user_info' => [
     353                    'username' => $order->billing_last_name . $order->billing_first_name,
     354                    'phone' => (empty($order->get_billing_phone()) ? '010-0000-0000' : $order->get_billing_phone()),
     355                    'email' => $order->billing_email,
     356                    'addr' => strip_tags(implode(' ', [
     357                        $order->get_billing_city(),
     358                        $order->get_billing_address_1(),
     359                        $order->get_billing_address_2()
     360                    ]))
     361                ]
     362            ];
     363
     364            return [
     365                'result' => 'success',
     366                'order_key' => $order->order_key,
     367                'order_id' => $order_id,
     368                'order_data' => $order_data,
     369                'checkout_url' => add_query_arg([
     370                    'wc-api' => self::PAYMENT_SUBMIT,
     371                    'order_id' => $order_id
     372                ], $checkout_url),
     373            ];
     374        }
     375
     376        public function bootpay_login_redirect($redirect_to, $request, $user)
     377        {
    363378//          exit;
    364             return $redirect_to;
    365         }
    366 
    367         /**
    368          * 결제 취소 관련 로직
    369          * 부트페이 서버로 부터 결제가 취소가 실패한 경우엔
    370          * alert으로 메세지를 보이도록 wp_error를 리턴한다.
    371          *
    372          * @param int    $order_id
    373          * @param null   $amount
    374          * @param string $reason
    375          *
    376          * @return bool|WP_Error
    377          */
    378 
    379         public function process_refund( $order_id, $amount = null, $reason = '' ) {
    380             $order      = new WC_Order( $order_id );
    381             $receipt_id = $order->get_meta( 'bootpay_receipt_id' );
    382             BootpayApi::setConfig( $this->get_option( 'rest_api_key' ), $this->get_option( 'private_key' ) );
    383             $response = BootpayApi::cancel( [
    384                 'receipt_id' => $receipt_id,
    385                 'name'       => __( '판매자', self::BOOTPAY_WC_DOMAIN ),
    386                 'reason'     => '판매자 취소',
    387                 'price'      => $amount
    388             ] );
    389 
    390             if( $response->status == 200 ) {
    391                 $result = $response->data;
    392                 // 모두 결제 취소가 된 경우
    393                 if( (int) $result->remain_price == 0 ) {
    394                     $order->add_order_note( sprintf( __( "%s원 모두 취소 됨", self::BOOTPAY_WC_DOMAIN ), number_format( (int) $amount ) ) );
    395                     $order->update_status( 'refunded' );
    396                 } else {
    397                     $order->add_order_note( sprintf( __( " %s원 부분 취소 됨", self::BOOTPAY_WC_DOMAIN ), number_format( (int) $amount ) ) );
    398                 }
    399 
    400                 return true;
    401             } else {
    402                 $message = sprintf( __( "결제 취소 실패 %s", self::BOOTPAY_WC_DOMAIN ), $response->message );
    403                 $order->add_order_note( $message );
    404 
    405                 return new WP_Error( 'error', $message );
    406             }
    407         }
    408 
    409         public function ajax_bootpay_payment_info() {
    410 
    411         }
    412 
    413         /**
    414          * 결제 완료후 Validation을 한다.
    415          * Bootpay Rest를 이용하여 결제 정보를 검증한다.
    416          * @return WP_Error
    417          */
    418         public function payment_validation() {
    419             $receipt_id = $_GET['receipt_id'];
    420             $order_id   = $_GET['order_id'];
    421 
    422             if( ! empty( $receipt_id ) && ! empty( $order_id ) ) {
    423                 $order = new WC_Order( $order_id );
    424                 if( in_array( $order->get_status(), ['processing', 'completed'] ) ) {
    425                     $order->add_order_note( __( '이미 결제 처리가 완료되었습니다.', self::BOOTPAY_WC_DOMAIN ) );
    426 
    427                     return new WP_Error( 'error', __( '이미 결제 처리가 완료되었습니다.', self::BOOTPAY_WC_DOMAIN ) );
    428                 }
    429 
    430                 BootpayApi::setConfig( $this->get_option( 'rest_api_key' ), $this->get_option( 'private_key' ) );
    431                 try {
    432                     $response = BootpayApi::confirm( [
    433                         'receipt_id' => $receipt_id
    434                     ] );
    435                 } catch( Exception $e ) {
    436                     $order->update_status( 'failed' );
    437                     $order->add_order_note( __( '결제가 원활히 진행되지 못했습니다.', self::BOOTPAY_WC_DOMAIN ) );
    438 
    439                     return new WP_Error( 'error', __( '결제가 원활히 진행되지 못했습니다.', self::BOOTPAY_WC_DOMAIN ) );
    440                 }
    441                 $result = $response->data;
    442                 if( $response->status == 200 && $result ) {
    443                     if( $result->status == 1 || ( $result->method == 'vbank' && $result->status == 2 ) ) {
    444                         if( (int) $result->price != (int) $order->get_total() ) {
    445                             $order->add_order_note( __( '결제된 금액이 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN ) );
    446 
    447                             return new WP_Error( 'error', __( '결제된 금액이 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN ) );
    448                         }
    449                         if( $order_id != $result->order_id ) {
    450                             $order->add_order_note( __( '결제 정보가 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN ) );
    451 
    452                             return new WP_Error( 'error', __( '결제 정보가 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN ) );
    453                         }
    454                         $transaction_id = $order->get_transaction_id();
    455                         if( $result->method == 'vbank' ) {
    456                             $order->update_status( 'wc-wating-bank', __( '입금대기', self::BOOTPAY_WC_DOMAIN ) );
    457                             $order->set_payment_method( $this->id );
    458                             $order->set_payment_method_title( $this->get_payment_method_title( $result ) );
    459                             $order->add_order_note( $this->get_payment_method_title( $result ) . __( ' 입금대기', self::BOOTPAY_WC_DOMAIN ) );
    460                             add_post_meta( $order_id, 'bootpay_receipt_id', $result->receipt_id );
    461                             add_post_meta( $order_id, 'bootpay_pg_name', $result->pg_name );
    462                             add_post_meta( $order_id, 'bootpay_method_name', $result->method_name );
    463                             add_post_meta( $order_id, 'bootpay_pg', $result->pg );
    464                             add_post_meta( $order_id, 'bootpay_method', $result->method );
    465                             add_post_meta( $order_id, 'bootpay_bankname', $result->payment_data->bankname );
    466                             add_post_meta( $order_id, 'bootpay_holder', $result->payment_data->accountholder );
    467                             add_post_meta( $order_id, 'bootpay_account', $result->payment_data->account );
    468                             add_post_meta( $order_id, 'bootpay_username', $result->payment_data->username );
    469                             add_post_meta( $order_id, 'bootpay_expire', $result->payment_data->expiredate );
    470                         } else {
    471                             // TODO: 나중에 Float형으로 변경해야 한다.
    472 
    473                             $order->payment_complete( $transaction_id );
    474                             $order->set_payment_method( $this->id );
    475                             $order->set_payment_method_title( $this->get_payment_method_title( $result ) );
    476                             $order->add_order_note( $this->get_payment_method_title( $result ) . __( ' 로 지불됨', self::BOOTPAY_WC_DOMAIN ) );
    477                             add_post_meta( $order_id, 'bootpay_receipt_id', $result->receipt_id );
    478                             add_post_meta( $order_id, 'bootpay_pg_name', $result->pg_name );
    479                             add_post_meta( $order_id, 'bootpay_method_name', $result->method_name );
    480                             add_post_meta( $order_id, 'bootpay_pg', $result->pg );
    481                             add_post_meta( $order_id, 'bootpay_method', $result->method );
    482                         }
    483                         // 구매가 완료되었으므로 카트를 지운다.
    484                         wc_empty_cart();
    485                         wp_redirect( $order->get_checkout_order_received_url() );
    486                     }
    487                 } else {
    488                     $order->add_order_note( $result->message );
    489 
    490                     return new WP_Error( 'error', $result->message );
    491                 }
    492             } else {
    493                 return new WP_Error( 'error', __( '잘못된 결제 접근 입니다.', self::BOOTPAY_WC_DOMAIN ) );
    494             }
    495         }
    496 
    497         /**
    498          * 가상계좌 입금시 Notification 처리하는 곳
    499          */
    500         public function vbank_notification() {
    501             $receipt_id  = $_POST['receipt_id'];
    502             $order_id    = $_POST['order_id'];
    503             $price       = (int) $_POST['price'];
    504             $private_key = $_POST['private_key'];
    505             // 가상 계좌만 처리하고 나머지는 처리하지 않는다.
    506             // 서버에 질의하여 검증하는 로직이 있으므로 다른 결제는 유효성 검사를 하지 않는다. ( 중복 방지 )
    507             if( $_POST['method'] == 'vbank' ) {
    508                 $order = new WC_Order( $order_id );
    509                 if( in_array( $order->get_status(), ['processing', 'completed'] ) ) {
    510                     $order->add_order_note( __( '이미 결제 처리가 완료되었습니다.', self::BOOTPAY_WC_DOMAIN ) );
    511                     echo 'error 1';
    512                     exit;
    513                 }
    514                 if( $this->get_option( 'private_key' ) != $private_key ) {
    515                     $order->add_order_note( __( '결제 비밀키가 일치하지 않아 가상계좌 결제가 승인되지 않았습니다.', self::BOOTPAY_WC_DOMAIN ) );
    516                     echo 'error 2';
    517                     exit;
    518                 }
    519                 if( (int) $price != (int) $order->get_total() ) {
    520                     $order->add_order_note( __( '결제된 금액이 일치하지 않아 가상계좌 결제가 승인이 되지 않았습니다.', self::BOOTPAY_WC_DOMAIN ) );
    521                     echo 'error 3';
    522                     exit;
    523                 }
    524                 $transaction_id = $order->get_transaction_id();
    525                 $order->payment_complete( $transaction_id );
    526                 $order->update_status( 'processing' );
    527                 $order->set_payment_method( $this->id );
    528                 $order->set_payment_method_title( sprintf( "%s - %s", $_POST['pg_name'], $_POST['method_name'] ) );
    529                 $order->add_order_note( sprintf( "%s - %s", $_POST['pg_name'], $_POST['method_name'] ) . __( ' 로 지불됨', self::BOOTPAY_WC_DOMAIN ) );
    530                 add_post_meta( $order_id, 'bootpay_receipt_id', $receipt_id );
    531                 add_post_meta( $order_id, 'bootpay_pg_name', $_POST['pg_name'] );
    532                 add_post_meta( $order_id, 'bootpay_method_name', $_POST['method_name'] );
    533                 add_post_meta( $order_id, 'bootpay_pg', $_POST['pg'] );
    534                 add_post_meta( $order_id, 'bootpay_method', $_POST['method'] );
    535             }
    536             echo 'OK';
    537             exit;
    538         }
    539 
    540         private function get_payment_method_title( $result ) {
    541             return sprintf( "부트페이 [%s - %s]", $result->pg_name, $result->method_name );
    542         }
    543 
    544         private function currentVersion() {
    545             return self::CURRENT_VERSION;
    546         }
    547 
    548         /**
    549          * @param      $file - Template 파일명
    550          * @param null $data - Template에서 사용할 Local Variable
    551          *                   View Template 기본 엔진 기능
    552          */
    553         private function renderFile( $file, $data = null ) {
    554             $template_path = __DIR__ . '/templates/' . $file;
    555             if( file_exists( $template_path ) ) {
    556                 if( ! is_null( $data ) && is_array( $data ) ) {
    557                     foreach( $data as $key => $value ) {
    558                         $$key = $value;
    559                     }
    560                 }
    561                 ob_start();
    562                 include( $template_path );
    563                 ob_end_flush();
    564             } else {
    565                 $this->renderError( __( "$template_path 파일이 없습니다.", self::BOOTPAY_WC_DOMAIN ) );
    566             }
    567 
    568             return;
    569         }
    570 
    571         /**
    572          * 에러가 났을 경우 에러를 뿌리고 바로 나간다.
    573          * javascript console.error도 함께 출력한다.
    574          *
    575          * @param $msg
    576          */
    577         private function renderError( $msg, $console = true ) {
    578             $this->renderFile( 'error.php', [
    579                 'errorMsg' => $msg,
    580                 'console'  => $console
    581             ] );
    582             exit;
    583         }
    584 
    585         private function renderJson( $response ) {
    586             header( 'Content-type: application/json' );
    587             echo json_encode( $response );
    588             wp_die();
    589         }
    590     }
    591 
    592     new WC_Gateway_Bootpay();
     379            return $redirect_to;
     380        }
     381
     382        /**
     383         * 결제 취소 관련 로직
     384         * 부트페이 서버로 부터 결제가 취소가 실패한 경우엔
     385         * alert으로 메세지를 보이도록 wp_error를 리턴한다.
     386         *
     387         * @param int $order_id
     388         * @param null $amount
     389         * @param string $reason
     390         *
     391         * @return bool|WP_Error
     392         */
     393
     394        public function process_refund($order_id, $amount = null, $reason = '')
     395        {
     396            $order = new WC_Order($order_id);
     397            $receipt_id = $order->get_meta('bootpay_receipt_id');
     398            BootpayApi::setConfig($this->get_option('rest_api_key'), $this->get_option('private_key'));
     399            $response = BootpayApi::cancel([
     400                'receipt_id' => $receipt_id,
     401                'name' => __('판매자', self::BOOTPAY_WC_DOMAIN),
     402                'reason' => '판매자 취소',
     403                'price' => $amount
     404            ]);
     405
     406            if ($response->status == 200) {
     407                $result = $response->data;
     408                // 모두 결제 취소가 된 경우
     409                if ((int)$result->remain_price == 0) {
     410                    $order->add_order_note(sprintf(__("%s원 모두 취소 됨", self::BOOTPAY_WC_DOMAIN), number_format((int)$amount)));
     411                    $order->update_status('refunded');
     412                } else {
     413                    $order->add_order_note(sprintf(__(" %s원 부분 취소 됨", self::BOOTPAY_WC_DOMAIN), number_format((int)$amount)));
     414                }
     415
     416                return true;
     417            } else {
     418                $message = sprintf(__("결제 취소 실패 %s", self::BOOTPAY_WC_DOMAIN), $response->message);
     419                $order->add_order_note($message);
     420
     421                return new WP_Error('error', $message);
     422            }
     423        }
     424
     425        public function ajax_bootpay_payment_info()
     426        {
     427
     428        }
     429
     430        /**
     431         * 결제 완료후 Validation을 한다.
     432         * Bootpay Rest를 이용하여 결제 정보를 검증한다.
     433         * @return WP_Error
     434         */
     435        public function payment_validation()
     436        {
     437            $receipt_id = $_GET['receipt_id'];
     438            $order_id = $_GET['order_id'];
     439
     440            if (!empty($receipt_id) && !empty($order_id)) {
     441                $order = new WC_Order($order_id);
     442                if (in_array($order->get_status(), ['processing', 'completed'])) {
     443                    $order->add_order_note(__('이미 결제 처리가 완료되었습니다.', self::BOOTPAY_WC_DOMAIN));
     444
     445                    return new WP_Error('error', __('이미 결제 처리가 완료되었습니다.', self::BOOTPAY_WC_DOMAIN));
     446                }
     447
     448                BootpayApi::setConfig($this->get_option('rest_api_key'), $this->get_option('private_key'));
     449                try {
     450                    $response = BootpayApi::confirm([
     451                        'receipt_id' => $receipt_id
     452                    ]);
     453                } catch (Exception $e) {
     454                    $order->update_status('failed');
     455                    $order->add_order_note(__('결제가 원활히 진행되지 못했습니다.', self::BOOTPAY_WC_DOMAIN));
     456
     457                    return new WP_Error('error', __('결제가 원활히 진행되지 못했습니다.', self::BOOTPAY_WC_DOMAIN));
     458                }
     459                $result = $response->data;
     460                if ($response->status == 200 && $result) {
     461                    if ($result->status == 1 || ($result->method == 'vbank' && $result->status == 2)) {
     462                        if ((int)$result->price != (int)$order->get_total()) {
     463                            $order->add_order_note(__('결제된 금액이 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN));
     464
     465                            return new WP_Error('error', __('결제된 금액이 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN));
     466                        }
     467                        if ($order_id != $result->order_id) {
     468                            $order->add_order_note(__('결제 정보가 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN));
     469
     470                            return new WP_Error('error', __('결제 정보가 일치하지 않습니다.', self::BOOTPAY_WC_DOMAIN));
     471                        }
     472                        $transaction_id = $order->get_transaction_id();
     473                        if ($result->method == 'vbank') {
     474                            $order->update_status('wc-wating-bank', __('입금대기', self::BOOTPAY_WC_DOMAIN));
     475                            $order->set_payment_method($this->id);
     476                            $order->set_payment_method_title($this->get_payment_method_title($result));
     477                            $order->add_order_note($this->get_payment_method_title($result) . __(' 입금대기', self::BOOTPAY_WC_DOMAIN));
     478                            add_post_meta($order_id, 'bootpay_receipt_id', $result->receipt_id);
     479                            add_post_meta($order_id, 'bootpay_pg_name', $result->pg_name);
     480                            add_post_meta($order_id, 'bootpay_method_name', $result->method_name);
     481                            add_post_meta($order_id, 'bootpay_pg', $result->pg);
     482                            add_post_meta($order_id, 'bootpay_method', $result->method);
     483                            add_post_meta($order_id, 'bootpay_bankname', $result->payment_data->bankname);
     484                            add_post_meta($order_id, 'bootpay_holder', $result->payment_data->accountholder);
     485                            add_post_meta($order_id, 'bootpay_account', $result->payment_data->account);
     486                            add_post_meta($order_id, 'bootpay_username', $result->payment_data->username);
     487                            add_post_meta($order_id, 'bootpay_expire', $result->payment_data->expiredate);
     488                        } else {
     489                            // TODO: 나중에 Float형으로 변경해야 한다.
     490
     491                            $order->payment_complete($transaction_id);
     492                            $order->set_payment_method($this->id);
     493                            $order->set_payment_method_title($this->get_payment_method_title($result));
     494                            $order->add_order_note($this->get_payment_method_title($result) . __(' 로 지불됨', self::BOOTPAY_WC_DOMAIN));
     495                            add_post_meta($order_id, 'bootpay_receipt_id', $result->receipt_id);
     496                            add_post_meta($order_id, 'bootpay_pg_name', $result->pg_name);
     497                            add_post_meta($order_id, 'bootpay_method_name', $result->method_name);
     498                            add_post_meta($order_id, 'bootpay_pg', $result->pg);
     499                            add_post_meta($order_id, 'bootpay_method', $result->method);
     500                        }
     501                        // 구매가 완료되었으므로 카트를 지운다.
     502                        wc_empty_cart();
     503                        wp_redirect($order->get_checkout_order_received_url());
     504                    }
     505                } else {
     506                    $order->add_order_note($result->message);
     507
     508                    return new WP_Error('error', $result->message);
     509                }
     510            } else {
     511                return new WP_Error('error', __('잘못된 결제 접근 입니다.', self::BOOTPAY_WC_DOMAIN));
     512            }
     513        }
     514
     515        /**
     516         * 가상계좌 입금시 Notification 처리하는 곳
     517         */
     518        public function vbank_notification()
     519        {
     520            $receipt_id = $_POST['receipt_id'];
     521            $order_id = $_POST['order_id'];
     522            $price = (int)$_POST['price'];
     523            $private_key = $_POST['private_key'];
     524            // 가상 계좌만 처리하고 나머지는 처리하지 않는다.
     525            // 서버에 질의하여 검증하는 로직이 있으므로 다른 결제는 유효성 검사를 하지 않는다. ( 중복 방지 )
     526            if ($_POST['method'] == 'vbank') {
     527                $order = new WC_Order($order_id);
     528                if (in_array($order->get_status(), ['processing', 'completed'])) {
     529                    $order->add_order_note(__('이미 결제 처리가 완료되었습니다.', self::BOOTPAY_WC_DOMAIN));
     530                    echo 'error 1';
     531                    exit;
     532                }
     533                if ($this->get_option('private_key') != $private_key) {
     534                    $order->add_order_note(__('결제 비밀키가 일치하지 않아 가상계좌 결제가 승인되지 않았습니다.', self::BOOTPAY_WC_DOMAIN));
     535                    echo 'error 2';
     536                    exit;
     537                }
     538                if ((int)$price != (int)$order->get_total()) {
     539                    $order->add_order_note(__('결제된 금액이 일치하지 않아 가상계좌 결제가 승인이 되지 않았습니다.', self::BOOTPAY_WC_DOMAIN));
     540                    echo 'error 3';
     541                    exit;
     542                }
     543                $transaction_id = $order->get_transaction_id();
     544                $order->payment_complete($transaction_id);
     545                $order->update_status('processing');
     546                $order->set_payment_method($this->id);
     547                $order->set_payment_method_title(sprintf("%s - %s", $_POST['pg_name'], $_POST['method_name']));
     548                $order->add_order_note(sprintf("%s - %s", $_POST['pg_name'], $_POST['method_name']) . __(' 로 지불됨', self::BOOTPAY_WC_DOMAIN));
     549                add_post_meta($order_id, 'bootpay_receipt_id', $receipt_id);
     550                add_post_meta($order_id, 'bootpay_pg_name', $_POST['pg_name']);
     551                add_post_meta($order_id, 'bootpay_method_name', $_POST['method_name']);
     552                add_post_meta($order_id, 'bootpay_pg', $_POST['pg']);
     553                add_post_meta($order_id, 'bootpay_method', $_POST['method']);
     554            }
     555            echo 'OK';
     556            exit;
     557        }
     558
     559        private function get_payment_method_title($result)
     560        {
     561            return sprintf("부트페이 [%s - %s]", $result->pg_name, $result->method_name);
     562        }
     563
     564        private function currentVersion()
     565        {
     566            return self::CURRENT_VERSION;
     567        }
     568
     569        /**
     570         * @param      $file - Template 파일명
     571         * @param null $data - Template에서 사용할 Local Variable
     572         *                   View Template 기본 엔진 기능
     573         */
     574        private function renderFile($file, $data = null)
     575        {
     576            $template_path = __DIR__ . '/templates/' . $file;
     577            if (file_exists($template_path)) {
     578                if (!is_null($data) && is_array($data)) {
     579                    foreach ($data as $key => $value) {
     580                        $$key = $value;
     581                    }
     582                }
     583                ob_start();
     584                include($template_path);
     585                ob_end_flush();
     586            } else {
     587                $this->renderError(__("$template_path 파일이 없습니다.", self::BOOTPAY_WC_DOMAIN));
     588            }
     589
     590            return;
     591        }
     592
     593        /**
     594         * 에러가 났을 경우 에러를 뿌리고 바로 나간다.
     595         * javascript console.error도 함께 출력한다.
     596         *
     597         * @param $msg
     598         */
     599        private function renderError($msg, $console = true)
     600        {
     601            $this->renderFile('error.php', [
     602                'errorMsg' => $msg,
     603                'console' => $console
     604            ]);
     605            exit;
     606        }
     607
     608        private function renderJson($response)
     609        {
     610            header('Content-type: application/json');
     611            echo json_encode($response);
     612            wp_die();
     613        }
     614    }
     615
     616    new WC_Gateway_Bootpay();
    593617}
  • woo-bootpay/trunk/readme.txt

    r1858733 r1888627  
    55Requires at least: 3.6
    66Tested up to: 4.9.5
    7 Stable tag: 1.1.10
     7Stable tag: 1.1.11
    88License: GPLv2 or later
    99License URI: http://www.gnu.org/licenses/gpl-2.0.html
     
    1212
    1313== Description ==
     14
     15버전 1.1.11
     16bootpay 2.0.6 버전 업데이트
     17다른 결제 수단 함께 사용 가능하도록 업데이트
     18
    1419버전 1.1.10
    1520Gateway Action 중복 등록 관리 Singleton Semaphore 추가
Note: See TracChangeset for help on using the changeset viewer.