简体   繁体   English

使用 PHP json_decode 解析 JavaScript JSON

[英]Parse JavaScript JSON with PHP json_decode

I am running in situation where I extract JSON string from html page that pass it to json_decode , some times it success and some times the json_decode return null, how to improve my solution to be 100% JSON compatible with json_decode ?我在从html页面提取 JSON 字符串并将其传递给json_decode情况下运行,有时它成功,有时json_decode返回 null,如何改进我的解决方案,使其与json_decode 100% JSON 兼容?

This is the string I extract, sorry it is too long: https://pastebin.com/aMavjffY这是我提取的字符串,抱歉太长了: https : //pastebin.com/aMavjffY

My solution:我的解决方案:

$json_str = html_entity_decode( THE_STRING_FROM_PASTBIN, ENT_QUOTES );
$lots_json = explode( ';', $json_str );
$num_items = count( $lots_json ) - 1;
$lot_json = '';
for( $i = 0; $i < $num_items; ++$i ) {
    // $lot_json will have now a valid JSON that can be parse with JavaScript JSON.parse()
    $lot_json = str_replace( 'ECAT.lot[\'' . ($i + 1) . '\']=', '', $lots_json[$i] );
    $original_lot_json = $lot_json;

    // Convert any " to a character chosen by us to not break the JSON format
    // but we have to convert it back to '
    // ALso convert 's to ***s and than get it back
    $lot_json = str_replace( '"', '***', $lot_json );

    $lot_json = str_replace( array( "{'", "':", ": '", ":'", "',", ",'", "'}", "['", "']" ), 
                             array( '{"', '":', ': "', ':"', '",', ',"', '"}', '["', '"]' ), $lot_json );

    // Convert it back
    $lot_json = str_replace( '***', '\'', $lot_json );

    $tmp_lot_json = $lot_json;
    $lot_json = json_decode( $lot_json, 1 );
    if( $lot_json == null ) {
        echo 'doGetItemUrlList json_decode fails ' . print_r( $tmp_lot_json, 1 );
        echo 'doGetItemUrlList original_lot_json ' . print_r( $original_lot_json, 1 )  );
    }
}

As everybody already said your data is not valid JSON.It is JavaScript object but not valid Json at all.However you can build your own fake Json decoder.For the example I remove the assignation in your data and reduce the length...正如大家已经说过的,您的数据不是有效的 JSON。它是 JavaScript 对象,但根本不是有效的 Json。但是,您可以构建自己的假 Json 解码器。例如,我删除了数据中的分配并减少了长度...

given this fake Json :鉴于这个假 Json :

$fake=<<<'EOL'
{'id':'299','saleName':'Yellow Ball: The Frank and Lorna Dunphy 
Collection 
Online','lotItemId':'8T76S','saleNumber':'L18622','image':'/content/dam/stb/lots/L18/L18622/L18622_8T76S_1.jpg','gua
ranteeLine':'DAMIEN 
HIRST','title':'FRANK','path':'/data/events/2018/yellowball-online-l18622/catalogue/lot_167810653','order':29900,'jc
rLastModifiedDate':1529396163248,'isSE':false,'isSold':false,'isPast':false,'video':'','audio':'','objectDate':'','e
stimateTxt':'<img src="/content/dam/default/lotSymbols/symb_ArtistResaleRight.gif" />400-600 
GBP','lowEst':400.0,'highEst':600.0,'currency':'GBP','salePrice':0.0,'artist':'Hirst, Damien','medium':['Works on 
paper'],'genre':['Contemporary'],'type':['Figurative','Portrait'],'vintage':[],'size':[],'category':[],'isArtnet':fa
lse,'isRegAvail':true,'isBidCutoff':86400000,'isEstRequest':false,'hasBidLive':false,'startTime':1537538400834,'endT
ime':1537549200834,'hasBidLive':false,'isRestrict':false,'isLiveNow':false,'isWine':false,'isClosed':false,'showRegT
oBidLink':true,'isHideSaleTime':false,'featVidPath':'','useExternal':false,'featVidId':'','featBlogPath':'','wineLin
k':'http://www.sothebyswinelive.com/main.cfm?P=WebcastRegistrationForm','bidNowLink':'/en/attend-auction.bidlive.htm
l/2018/yellowball-online-l18622','addToCalLink':'/data/events/2018/yellowball-online-l18622','regToBidLink':'2018/ye
llowball-online-l18622','preSaleLot':true,'condRep':'/en/auctions/ecatalogue/2018/yellowball-online-l18622/lot.299.h
tml#conditionsOfSaleModal','soldPast':false,'isLiveNowWine':false,'onlineBiddingAvailableWine':false,'bidNowLinkWine
': '','altTitle':'FRANK'}
EOL
;

you can build a function like this:您可以构建这样的函数:

         function fakeJsonDecode($data){

            return  eval('return '.join('',array_slice(array_map(
                  function($v){
                      if(is_array($v)){
                        $v[1]=str_replace('’','"',$v[1]);
                        $v[1]=str_replace('‘','"',$v[1]);
                        $v[1]=trim($v[1]);
                        if(!empty($v[1])&&$v[1][0]==='<'&&$v[1][strlen($v[1])-1]==='>')
                            $v[1]=substr($v[1],1,-1);
                        $v=$v[1];
                    }else{
                        if($v==='{') $v='[';
                        if($v==='}') $v=']';
                        if($v===':') $v='=>';
                        if($v==='<') $v='"';
                        if($v==='>') $v='"';
                    }

                    return $v;

                },token_get_all('<?php '.$data.' ?>')),1,-1)).';');


        }

        print_r(fakeJsonDecode($fake));

and the output is:输出是:

Array
(
    [id] => 299
    [saleName] => Yellow Ball: The Frank and Lorna Dunphy 
Collection 
Online
    [lotItemId] => 8T76S
    [saleNumber] => L18622
    [image] => /content/dam/stb/lots/L18/L18622/L18622_8T76S_1.jpg
    [gua
ranteeLine] => DAMIEN 
HIRST
    [title] => FRANK
    [path] => /data/events/2018/yellowball-online-l18622/catalogue/lot_167810653
    [order] => 29900
    [jc
rLastModifiedDate] => 1529396163248
    [isSE] => 
    [isSold] => 
    [isPast] => 
    [video] => 
    [audio] => 
    [objectDate] => 
    [e
stimateTxt] => 400-600 
GBP
    [lowEst] => 400
    [highEst] => 600
    [currency] => GBP
    [salePrice] => 0
    [artist] => Hirst, Damien
    [medium] => Array
        (
            [0] => Works on 
paper
        )

    [genre] => Array
        (
            [0] => Contemporary
        )

    [type] => Array
        (
            [0] => Figurative
            [1] => Portrait
        )

    [vintage] => Array
        (
        )

    [size] => Array
        (
        )

    [category] => Array
        (
        )

    [isArtnet] => 
    [isRegAvail] => 1
    [isBidCutoff] => 86400000
    [isEstRequest] => 
    [hasBidLive] => 
    [startTime] => 1537538400834
    [endT
ime] => 1537549200834
    [isRestrict] => 
    [isLiveNow] => 
    [isWine] => 
    [isClosed] => 
    [showRegT
oBidLink] => 1
    [isHideSaleTime] => 
    [featVidPath] => 
    [useExternal] => 
    [featVidId] => 
    [featBlogPath] => 
    [wineLin
k] => http://www.sothebyswinelive.com/main.cfm?P=WebcastRegistrationForm
    [bidNowLink] => /en/attend-auction.bidlive.htm
l/2018/yellowball-online-l18622
    [addToCalLink] => /data/events/2018/yellowball-online-l18622
    [regToBidLink] => 2018/ye
llowball-online-l18622
    [preSaleLot] => 1
    [condRep] => /en/auctions/ecatalogue/2018/yellowball-online-l18622/lot.299.h
tml#conditionsOfSaleModal
    [soldPast] => 
    [isLiveNowWine] => 
    [onlineBiddingAvailableWine] => 
    [bidNowLinkWine
] => 
    [altTitle] => FRANK
)

so you need to use my function on $original_lot_json所以你需要在$original_lot_json上使用我的function

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM