Bagaimana cara menentukan nomor baris saat ini di JavaScript?

Jawaban:

70

var thisline = new Error().lineNumber

Jika itu tidak berhasil di lingkungan apa pun yang Anda gunakan, Anda dapat mencoba:

var stack = new Error().stack

Kemudian cari melalui tumpukan untuk nomor baris.

z5h
sumber
3
Tidak akan berfungsi di IE, lineNumberproperti tidak ada di objek kesalahan. Begitu pula stack:-)
Andy E
1
ada nomor baris di suatu tempat di IE. Saya tahu ini karena ketika javascript saya melempar kesalahan mengatakan itu pada baris dengan angka lebih dari 100 juta.
Malfist
saya tidak mendapatkan nomor yang benar, itu 1350 padahal seharusnya 1250.
Fzs2
1
Masalah: jika Anda menggunakan PHP, "kode sumber" yang dilihat oleh javascript bukanlah kode sumber asli, sehingga nomor barisnya salah. (Mungkin itu yang terjadi pada Hermann.) Apakah ada yang tahu cara membuat javascript melihat nomor baris kode sumber PHP asli? Solusinya mungkin melibatkan semacam pembuatan "peta sumber", tetapi saya tidak dapat menemukan cara melakukannya. Tentunya ini masalah yang terpecahkan, bukan ??
Dave Burton
Catatan: terkadang tumpukan / nomor baris tidak tersedia saat objek Kesalahan dibuat, hanya jika dilempar, misalnya di Skrip Google Apps - dalam hal ini lihat jawaban ini untuk solusinya.
pengguna202729
38

Kamu bisa memakai:

function test(){
    console.trace();
}

test();
baligena
sumber
1
Sejauh ini solusi paling sederhana dan bahkan berfungsi di MS Edge.
Bahaya
27

Sedikit lebih portabel antara berbagai browser dan versi browser (seharusnya berfungsi di Firefox, Chrome, dan IE10 +):

function ln() {
  var e = new Error();
  if (!e.stack) try {
    // IE requires the Error to actually be throw or else the Error's 'stack'
    // property is undefined.
    throw e;
  } catch (e) {
    if (!e.stack) {
      return 0; // IE < 10, likely
    }
  }
  var stack = e.stack.toString().split(/\r\n|\n/);
  // We want our caller's frame. It's index into |stack| depends on the
  // browser and browser version, so we need to search for the second frame:
  var frameRE = /:(\d+):(?:\d+)[^\d]*$/;
  do {
    var frame = stack.shift();
  } while (!frameRE.exec(frame) && stack.length);
  return frameRE.exec(stack.shift())[1];
}
jwatt.dll
sumber
Terima kasih. Saya menyesuaikan saran Anda menjadi ini: stackoverflow.com/a/37081135/470749
Ryan
1
Jika Anda menyesuaikan regex, Anda dapat mengembalikan nomor baris dan kolom: var frameRE = /:(\d+:\d+)[^\d]*$/;yang jauh lebih berguna, terutama saat JS diminimalkan menjadi satu baris panjang.
Quinn Comendant
Peringatan, tidak berfungsi di skrip ViolentMonkey untuk Chrome - Anda akan mendapatkan nomor palsu, tidak tahu mengapa.
Hanshenrik
5

Anda dapat mencoba mengurai sumber fungsi untuk mencari beberapa tanda.
Berikut ini contoh singkatnya (ya, ini sedikit kacau).

function foo()  
{       
    alert(line(1));
    var a;
    var b;      
    alert(line(2));
}   
foo();

function line(mark)
{
    var token = 'line\\(' + mark + '\\)';       
    var m = line.caller.toString().match(
        new RegExp('(^(?!.*' + token + '))|(' + token + ')', 'gm')) || [];
    var i = 0;
    for (; i < m.length; i++) if (m[i]) break;
    return i + 1;
}
Mikhail Nasyrov
sumber
3

Masukkan cuplikan berikut ke kode Anda:

console.debug("line:", /\(file:[\w\d/.-]+:([\d]+)/.exec(new Error().stack)[1]);
crishushu
sumber
ganti nama protokol sesuai kebutuhan (mis. "http:")
crishushu
1
Saya tidak bisa mendapatkan ini untuk bekerja. Saya mengerti TypeError: /\(http:[\w\d/.-]+:([\d]+)/.exec(...) is null.
Ryan
2

Anda dapat mencoba:

window.onerror = handleError;
function handleError(err, url, line){
    alert(err + '\n on page: ' + url + '\n on line: ' + line);
}

Kemudian lemparkan kesalahan di mana Anda ingin tahu (tidak terlalu diinginkan, tetapi mungkin membantu Anda jika Anda melakukan debug.

Catatan: window.onerrortidak ditentukan / ditangani di WebKit atau Opera (terakhir kali saya memeriksa)

scunliffe.dll
sumber
1
Perhatikan bahwa window.onerror tidak berfungsi di webkit: bugs.webkit.org/show_bug.cgi?id=8519
Annie
1
Menarik. Anda bahkan dapat membuat fungsi khusus throwAndResume(resumeFunction);yang akan menyimpan resumeFunction, membuang kesalahan, dan dalam log penanganan kesalahan Anda rinciannya kemudian memanggil resumeFunction untuk melanjutkan program Anda.
z5h
0

Murni orang tidak bisa mendapatkan nomor baris dari Error.stack, karena di Angular nomor baris adalah nomor baris dari kode yang dikompilasi. Tapi seseorang bisa mendapatkan info di mana metode kesalahan itu dibuat. Logger kelas dalam potongan kode ini menambahkan informasi ini ke entri buku catatan baru.

https://stackblitz.com/edit/angular-logger?file=src/app/Logger/logger.ts

Viree
sumber
-2

Jika kode Anda adalah JavaScript + PHP, maka nomor baris PHP saat ini tersedia dalam JavaScript sebagai konstanta literal, karena tersedia dalam PHP sebagai   <?= __LINE__ ?>

(Itu dengan asumsi Anda telah mengaktifkan tag pendek PHP.)

Jadi, misalnya, di JavaScript Anda bisa mengatakan:

this_php_line_number = <?= __LINE__ ?>;

Namun, jika Anda tidak berhati-hati, nomor baris PHP mungkin berbeda dari nomor baris JavaScript, karena PHP "memakan" baris sumber sebelum browser melihatnya. Jadi masalahnya adalah memastikan bahwa nomor baris PHP dan JavaScript Anda sama. Jika berbeda, penggunaan debugger JavaScript browser menjadi kurang menyenangkan.

Anda dapat memastikan nomor baris sama dengan menyertakan pernyataan PHP yang menulis jumlah baris baru yang benar yang diperlukan untuk menyinkronkan nomor baris sisi server (PHP) dan sisi browser (JavaScript).

Inilah tampilan kode saya:

<!DOCTYPE html>
<html lang="en">
<!-- Copyright 2016, 2017, me and my web site -->
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="initial-scale=1, user-scalable=yes">

<?php

...lots of PHP stuff here, including all PHP function definitions ...

echo str_repeat("\n",__LINE__-6); # Synchronize PHP and JavaScript line numbers
?>
<!-- *** this is line <?php echo __LINE__ . ' of ' . basename(__FILE__); ?> *** -->

  <title>My web page title</title>

...lots of HTML and JavaScript stuff here...

</body>
</html>
<!-- *** this is line <?php echo __LINE__ . ' of ' . basename(__FILE__); ?> *** -->

Kuncinya adalah pernyataan PHP ini:

echo str_repeat("\n",__LINE__-6);

Itu mengeluarkan cukup banyak baris baru untuk membuat nomor baris yang dilihat oleh JavaScript menjadi sama dengan nomor baris PHP. Semua definisi fungsi PHP, dll. Ada di atas, di depan baris itu.

Setelah baris itu, saya membatasi penggunaan PHP saya untuk kode yang tidak mengubah nomor baris.

"-6" menjelaskan fakta bahwa kode PHP saya dimulai pada baris 8. Jika Anda memulai kode PHP lebih awal, Anda akan mengurangi angka itu. Beberapa orang menempatkan PHP mereka tepat di bagian paling atas, bahkan di depan DOCTYPE.

(Garis meta viewport menonaktifkan Android Chrome "font boosting" sesuai T&J Stack Overflow ini: Chrome di Android mengubah ukuran font . Anggap saja boilerplate, yang dibutuhkan setiap halaman web.)

Baris berikut ini hanya untuk memverifikasi bahwa saya tidak melakukan kesalahan. Dilihat di debugger browser, atau dengan klik kanan / simpan-halaman-web, ini menjadi komentar HTML yang menunjukkan nama file sumber dan nomor baris yang benar:

<!-- *** this is line <?php echo __LINE__ . ' of ' . basename(__FILE__); ?> *** -->

menjadi:

<!-- *** this is line 1234 of my_file.php *** -->

Sekarang, di mana pun saya melihat nomor baris, apakah itu dalam pesan kesalahan atau di debugger JavaScript, itu benar. Nomor baris PHP dan nomor baris JavaScript selalu konsisten dan identik.

Dave Burton
sumber