v2.5.2
Giriş yap

NodJs veya Pph Curl ile Paraşüt web uygulamasına giriş?

trsherlock
1,004 defa görüntülendi

Merhaba arkadaşlar aşağıdaki web tabanlı Paraşüt ön muhasebe uygulamasına otomatik giriş yaptırmak istiyorum.

Php curl ile denemek istedim name = "authenticity_token" değeri de sayfada ile yüklendiği için direk giriş yaptırmadım. Oturum aç dediğim de arka planda post eder zannettim adres çubuğunu localhost/kullanici-girisi şeklinde değiştirerek post etti.
Beni aşan bir sorun yardımlarınız için şimdiden teşekkürler.

Paraşüt Giriş Bağlantısı
e-posta: [email protected]
şifre: parasut

<form class="new_user" id="new_user" action="/kullanici-girisi" accept-charset="UTF-8" method="post">
<input type="hidden" name="authenticity_token" value="smhvSLLINoDT4Y1KnXRU4NkXzRrcodaA8XHkSDKhMaYR6bDYjYKYJO5aUzet2hWZgoZ57FrglQytuR5oE4VAIA==">
<div class="l-col16 l-offset-s3 l-col-s10 l-offset-l5 l-col-l6">
<div class="form u-clearfix u-mt1 u-pv15">
<div class="form-content">
<input placeholder="E-posta Adresi" class="field" type="email" value="" name="user[email]" id="user_email">
<input placeholder="Parola" class="field u-mb1" type="password" name="user[password]" id="user_password">
<div class="u-textLeft u-pullRight u-pt05">
<input name="user[remember_me]" type="hidden" value="0">
<input class="u-pullLeft u-width1 u-mr025" style="margin-top:0.15rem;" type="checkbox" value="1" name="user[remember_me]" id="user_remember_me">
<label class="u-pullLeft" for="user_remember_me">Oturum açık kalsın</label>
</div>
<input type="submit" name="commit" value="OTURUM AÇ" class="button button-primary button-big u-pullLeft" id="Sign_In" data-disable-with="OTURUM AÇ">
</div>
</div>
</div>
</form>

NodeJs ile yaptığımda gelen sonuç: <html><body>You are being <a href="https://uygulama.parasut.com/tarayicinizi-guncelleyin">redirected</a>.</body></html>
Şifreyi hatalı post ettiğimde giriş sayfasının html sayfasını döküyor sanırsam Nodejs ile post başarılı fakat sorgu yapan tarayıcı ile ilgili bir problem.
Bu konuda da yardımcı olursanız sevinirim.

var request = require("request");
var HTMLParser = require('node-html-parser');


login()
function login() {
    var authenticity_token = {
        method: 'GET', url: 'https://uygulama.parasut.com/kullanici-girisi',
    };

    request(authenticity_token, function (error, response, body) {
        console.log(HTMLParser.parse(body).querySelector("input[name='authenticity_token']")["_attrs"]["value"])
        var options = {
            method: 'POST',
            url: 'https://uygulama.parasut.com/kullanici-girisi',
            qs:
            {
                authenticity_token: HTMLParser.parse(body).querySelector("input[name='authenticity_token']")["_attrs"]["value"],
                'user[email]': '[email protected]',
                'user[password]': 'parasut',
                'user[remember_me]': '0',
                commit: 'OTURUM AÇ'
            }
        };

        request(options, function (error, response, body) {
            if (error) throw new Error(error);
            console.log(body)
        });
    })
}
Cevap yaz
Cevaplar (6)
trsherlock
644 gün önce

Doğru diyorsun paylaşmam gerekirdi.
Yalnız muhasebe bürosunda çalıştığım için hem sorunu çözmek hem muhasebe işleri ile uğraşmak epey vaktimi almıştı.
O zamanlar aklımdan uçup gitmiş. :)

Oturum açtıktan sonra pro hesabın sayfası https://uygulama.parasut.com/id/

munzevi
644 gün önce

@trsherlock madem çözdün, kodunu ekleyip çözüldü yapsaydın ya. boşuna uğraştım : ) senin örneğin ile benim örneğimin çalışma prensipleri aslında aynı, farkı anlamak için senin kodunu çalıştırdım; aynı sonucu aldım 302. benim örneğimde de 302'yi tek tek takip ettiğim kısmı atarsak, aslında kodlama aynı kodlama. gözden kaçırdığım ne var burada anlamadım. madem senin ki çalışıyor, benimki de çalışmalı. niye giriş yapmıyorlar? başta bir şeyi eksik yaptım diye düşündüm ama, bi saniye şimdi anladım. id değerinizi bildiğiniz için, manuel istek gönderiyorsunuz muhtemelen. bu da buraya eklediğiniz kodun eksik olduğu anlamına geliyor, eğer şöyle yaparsam;

            $this->url = 'https://uygulama.parasut.com/accounts/426236/account';
            $this->curlGet(["curl" => $c, "post" => false]);

evet giriş yaptım

bunu en başta da yapabilirdim, önceki mesajda belirtmiştim {id}/accounta yönlendirmesi gerekiyor diye. elle url girmek doğru gelmedi bana, bu yüzden bana göre benim sınıfım hala başarısız; giriş yaptığı halde. hadi üşenmeyim başarılı hale getireyim dedim ama, curl ile bağlanırken, site beklenildiği gibi çalışmıyor. post istediğinin ardından alınan son 302'nin ardından https://uygulama.parasut.com adresine yapılan yönlendirmenin sayfayı accounts/426236/accounta yönlendirmesi gerekiyor. ama yönlendirmiyor. header da konuyla alakalı bilgi çıktılamadığı için, neticede elle url girmekten başka çare bırakmıyor gibi duruyor. neyse. çözdüğün halde bile eksik kod göndermen enteresan, konuyu hortlatan arkadaşa bari yardım için bıraksaydın kodu. diğer arkadaş için çalışan tam kod örneğini aşağıya bırakıyorum, eposta, şifre ve id bilgilerini düzenlemeniz yeterli olur;

error_reporting(E_ALL);
class Parasut{
    private $url     = 'https://uygulama.parasut.com/kullanici-girisi';
    private $eposta  = '[email protected]';
    private $sifre   = 'parasut';
    private $id      = 426236;
    private $hatirla = 0;
    function giris(){
        $curl = $this->curlCustom();
        echo $curl["status"] === true ? $curl["output"] : "curl bağlanamadı";
    }
    private function curlCustom(){
        $c = curl_init();
        $this->curlGet(["curl" => $c, "post" => false]);
        $sonuc = curl_exec($c);
        if(curl_getinfo($c, CURLINFO_RESPONSE_CODE) === 200){
            preg_match('/name="authenticity_token" value="(.*?)"/si', $sonuc, $token);
            $data = array(
                "authenticity_token" => $token[1],
                "user[email]"        => $this->eposta,
                "user[password]"     => $this->sifre,
                "user[remember_me]"  => $this->hatirla,
                "commit"             => "OTURUM AÇ"
            );
            $this->curlGet([
                "curl" => $c,
                "post" => true,
                "data" => http_build_query($data)
            ]);
            curl_exec($c);
            $this->url = sprintf('https://uygulama.parasut.com/accounts/%d/account', $this->id);
            $this->curlGet(["curl" => $c, "post" => false]);
            $curlInfo = array(
                "status"  => true,
                "request" => curl_getinfo($c,CURLINFO_HEADER_OUT),
                "output"  => curl_exec($c),
                "token"   => $token[1]
            );
        }else{
            $curlInfo = array("status"  => false);
        }
        curl_close($c);
        return $curlInfo;
    }
    private function curlGet($init){
        $key  = $init["post"] === true ? CURLOPT_POSTFIELDS : CURLOPT_HEADER;
        $val  = $init["post"] === true ? $init["data"] : false;
        return curl_setopt_array($init["curl"], [
            CURLOPT_URL            => $this->url,
            CURLOPT_RETURNTRANSFER => true,
            CURLOPT_SSL_VERIFYHOST => false,
            CURLOPT_SSL_VERIFYPEER => false,
            CURLINFO_HEADER_OUT    => true,
            CURLOPT_POST           => $init["post"],
            CURLOPT_COOKIESESSION  => true,
            CURLOPT_COOKIEJAR      => './cerez',
            CURLOPT_COOKIEFILE     => './cerez',
            $key                   => $val
        ]);
    }
}
trsherlock
644 gün önce

Ben konuyu paylaştığım zamanlarda sorunu php tarafında çözmüştüm yalnız ben kullanıcı id bilgisini bildiğim için giriş yaptıktan sonra direk istek attırıyorum.
Aşağıdaki kodlar oturum açmak için.

    $parasut_login = curl_init();
    curl_setopt($parasut_login, CURLOPT_URL, "https://uygulama.parasut.com/kullanici-girisi");
    curl_setopt($parasut_login, CURLOPT_REFERER, "https://uygulama.parasut.com/kullanici-girisi");
    curl_setopt($parasut_login, CURLOPT_USERAGENT, $_SERVER["HTTP_USER_AGENT"]);
    curl_setopt($parasut_login, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($parasut_login, CURLOPT_COOKIEJAR, "parasut.txt");
    curl_setopt($parasut_login, CURLOPT_COOKIEFILE, "parasut.txt");
    preg_match_all('<input type="hidden" name="authenticity_token" value="(.*?)">', curl_exec($parasut_login), $authenticity_token);
    
    curl_setopt($parasut_login, CURLOPT_URL, "https://uygulama.parasut.com/kullanici-girisi");
    curl_setopt($parasut_login, CURLOPT_REFERER, "https://uygulama.parasut.com/kullanici-girisi");
    curl_setopt($parasut_login, CURLOPT_USERAGENT, $_SERVER["HTTP_USER_AGENT"]);
    curl_setopt_array($parasut_login, [
    CURLOPT_USERAGENT => "https://uygulama.parasut.com/kullanici-girisi",
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_USERAGENT => $_SERVER["HTTP_USER_AGENT"],
    CURLOPT_POST => true,
    CURLOPT_FOLLOWLOCATION => false,
    CURLOPT_POSTFIELDS => [
        'authenticity_token' => $authenticity_token[1][0],
        'user[email]' => '[email protected]',
        'user[password]' => '****',
        'user[remember_me]' => '0',
        'commit' => 'OTURUM AÇ'
    ],
    CURLOPT_COOKIEFILE => 'parasut.txt'
    ]);
    curl_exec($parasut_login);

Aşağıdaki kodlar da satış faturalarını listelemek için...

$kid = 11111;
curl_setopt($parasut_login, CURLOPT_URL, "https://api.parasut.com/v4/$kid/sales_invoices?filter%5Barchived%5D=false&filter%5Brecurring%5D=false&filter%5Bquery%5D=&filter%5Bsharing_status%5D=&filter%5Bpayment_status%5D=&filter%5Bprint_status%5D=&filter%5Bissue_date%5D%5Bgteq%5D=" . date('Y-m-d', strtotime($donem)) . "&filter%5Bissue_date%5D%5Blteq%5D=" . date('Y-m-t', strtotime($donem)) . "&filter%5Bitem_type%5D=invoice%2Crefund%2Cestimate%2Cexport&filter%5Bcategory%5D=&filter%5Btag_ids%5D=&include=category%2Ctags%2Ccontact%2Cactive_e_document%2Cfailed_e_invoice&order_scope=order_by_remaining_desc&page%5Bnumber%5D=1");
curl_setopt_array($parasut_login, [
    CURLOPT_USERAGENT => "https://uygulama.parasut.com/",
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_USERAGENT => $_SERVER["HTTP_USER_AGENT"],
    CURLOPT_POST => false,
    CURLOPT_FOLLOWLOCATION => false,
    CURLOPT_MAXREDIRS => 0,
    CURLOPT_COOKIEFILE => 'parasut.txt'
]);

$result = json_decode(curl_exec($parasut_login), true);

Bir de çerezler konusunda COOKIEFILE ve COOKIEJAR kullanmaya gerek var mı emin değilim?
Ben şimdi interaktif ve defter beyan için oturum açma veri çekme ile ilgili uygulama yapmaya çalışıyorum oturum kapatma aşamasına kadar kullanmıyorum.
Sanırsam curl_close() kullanıldığı zaman gerek duyuluyor.

munzevi
644 gün önce

konuyu aktif görünce çözeyim istedim ama gözden kaçırdığım bir şeyler var sanırım. teoride çalışması gereken bir sınıf yazdım. ama umduğumdan fazla yönlendirme mevcuttu, önce followlocation ile takip edeyim dedim, baktım ki doğrulama için gereken çerez her yönlendirilmede yenisiyle değişiyor. o zaman sırasıyla takip edeyim dedim, son yönlendirmede id ile alakalı bir bağlantı vermesi daha sonrasında bunu {id}/account/ şeklinde yönlendirmesi gerekiyordu ama, 200 için doğrudan giriş sayfasına yönlendirdi. sanırım curl ayarlamalarındaki çerez yapısını kaldırıp, ilk bağlantıda üst bilgiden okuyarak devam etmem gerekiyordu. küçük bir ihtimal de refereransları doğru belirtmedim bundan da kaynaklanabilir. sıfırdan bir daha yazayım diye düşündüm ama, enerjim kalmadı. devam etmek isteyen varsa benim örneğim;

error_reporting(E_ALL);
class Parasut{
    private $url     = 'https://uygulama.parasut.com/kullanici-girisi';
    private $eposta  = '[email protected]';
    private $sifre   = 'parasut';
    private $hatirla = 0;
    function giris(){
        $curl = $this->curlCustom();
        echo $curl["status"] === true ? $curl["output"] : "hata";
    }
    private function curlCustom(){
        $c = curl_init();
        $this->curlGet(["curl" => $c, "post" => false, "cookie" => 0]);
        $sonuc = curl_exec($c);
        if(curl_getinfo($c, CURLINFO_RESPONSE_CODE) === 200){
            $httpRequest = preg_replace('/^.+\n/', '', curl_getinfo($c,CURLINFO_HEADER_OUT));
            preg_match('/name="authenticity_token" value="(.*?)"/si', $sonuc, $token);
            preg_match('/_parasut_session_production_(.*?)$/si', file_get_contents('./cerez'), $cerez);
            $cerez = "_parasut_session_production_=".trim($cerez[1]);
            $data = array(
                "authenticity_token" => $token[1],
                "user[email]"        => $this->eposta,
                "user[password]"     => $this->sifre,
                "user[remember_me]"  => $this->hatirla,
                "commit"             => "OTURUM AÇ"
            );
            $this->curlGet([
                "curl" => $c,
                "post" => true,
                "cookie" => $cerez,
                "data" => http_build_query($data)
            ]);
            $sonuc2 = curl_exec($c);
            $httpRequest2 = preg_replace('/^.+\n/', '', curl_getinfo($c,CURLINFO_HEADER_OUT));
            if(curl_getinfo($c, CURLINFO_RESPONSE_CODE) === 302){
                $reg = $this->cookieRegex([$httpRequest2, $sonuc2]);
                $this->url = $reg[1];
                $this->curlGet([
                    "curl" => $c,
                    "post" => false,
                    "cookie" => $reg[0],
                ]);
                $sonuc3 = curl_exec($c);
                $httpRequest3 = preg_replace('/^.+\n/', '', curl_getinfo($c,CURLINFO_HEADER_OUT));


                if(curl_getinfo($c, CURLINFO_RESPONSE_CODE) === 302){
                    $reg = $this->cookieRegex([$httpRequest3, $sonuc3]);
                    $this->url = $reg[1];
                    $this->curlGet([
                        "curl" => $c,
                        "post" => false,
                        "cookie" => $reg[0],
                    ]);
                    $sonuc4 = curl_exec($c);
                    $httpRequest4 = preg_replace('/^.+\n/', '', curl_getinfo($c,CURLINFO_HEADER_OUT));
                }
            }
            $curlInfo = array(
                "status"  => true,
                "request" => [$httpRequest, $httpRequest2, $httpRequest3, $httpRequest4],
                "output"  => $sonuc4,
                "token"   => $token[1]
            );
        }else{
            $curlInfo = array("status"  => false);
        }
        curl_close($c);
        return $curlInfo;
    }
    private function cookieRegex($header){
        preg_match('/cookie: _parasut_session_production_=(.*?)authority/si', $header[0], $cerez);
        preg_match('/Location: (.*?)Cache/si', $header[1], $url);
        return array(trim($cerez[1]), trim($url[1]));
    }
    private function curlGet($init){
        $key  = $init["post"] === true ? CURLOPT_POSTFIELDS : CURLOPT_HEADER;
        $val  = $init["post"] === true ? $init["data"] : true;
        return curl_setopt_array($init["curl"], [
            CURLOPT_URL            => $this->url,
            CURLOPT_RETURNTRANSFER => true,
            //CURLOPT_FOLLOWLOCATION => $init["post"],
            CURLOPT_SSL_VERIFYHOST => false,
            CURLOPT_SSL_VERIFYPEER => false,
            CURLINFO_HEADER_OUT    => true,
            CURLOPT_HTTPHEADER     => $this->getHeaders($init["cookie"]),
            CURLOPT_POST           => $init["post"],
            CURLOPT_COOKIESESSION  => true,
            CURLOPT_COOKIEJAR      => './cerez',
            CURLOPT_COOKIEFILE     => './cerez',
            CURLOPT_COOKIE         => $init["cookie"],
            $key                   => $val
        ]);
    }
    private function getHeaders($cerez){
        return array(
            'authority: uygulama.parasut.com',
            'accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9',
            'accept-language: tr-TR,tr;q=0.9,en-US;q=0.8,en;q=0.7',
            'cache-control: max-age=0',
            'content-type: application/x-www-form-urlencoded',
            "cookie: $cerez",
            'origin: https://uygulama.parasut.com',
            'referer: https://uygulama.parasut.com/kullanici-girisi',
            'sec-ch-ua: ".Not/A)Brand";v="99", "Google Chrome";v="103", "Chromium";v="103"',
            'sec-ch-ua-mobile: ?0',
            'sec-ch-ua-platform: "Windows"',
            'sec-fetch-dest: document',
            'sec-fetch-mode: navigate',
            'sec-fetch-site: same-origin',
            'sec-fetch-user: ?1',
            'upgrade-insecure-requests: 1',
            'user-agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36',
        );
    }
}

edit: api hazırlamışlar https://apidocs.parasut.com/ işinizi görmüyor mu, neden kullanmıyorsunuz?

trsherlock
644 gün önce

@alihan hangi konuda nodejs mi yoksa php mi?

alihan
644 gün önce

Aynı sorundan şu sıralarda ben de muzdaribim