Bagaimana saya bisa menggunakan Python untuk mendapatkan nama host sistem?

681

Saya sedang menulis program obrolan untuk jaringan lokal. Saya ingin dapat mengidentifikasi komputer dan mendapatkan nama komputer yang diatur pengguna dengan Python.

John
sumber

Jawaban:

1043

Gunakan socketdan gethostname()fungsinya. Ini akan menghasilkan hostnamekomputer tempat interpreter Python berjalan:

import socket
print(socket.gethostname())
Alex
sumber
70
yah, itu tidak benar. Ini berfungsi untuk saya offline dan di rumah, tetapi sekarang saya adalah kantor dan ini mengembalikan nama host yang berbeda.
DataGreed
74
Dan perhatikan bahwa untuk FQDN Anda dapat menggunakansocket.getfqdn()
Dave Forgac
31
@ DataGreed itu karena nama host Anda berubah. Bukan masalah python.
strickli
4
@ DataGreed 1. Saya cukup yakin itu bukan "acak", meskipun mungkin tampak seperti itu bagi Anda. 2. Pertanyaannya mengatakan "system hostname", bukan "system name". 3. Untuk sejumlah besar sistem (diakui tidak termasuk windows) nama host dan sistem adalah sama.
strickli
8
Hanya ingin tahu apa perbedaan antara socket.gethostname () dan os.uname () [1] atau platform.uname () [1]
LetsOMG
388

Keduanya sangat portabel:

import platform
platform.node()

import socket
socket.gethostname()

Solusi apa pun yang menggunakan variabel HOSTatau HOSTNAMElingkungan tidak portabel. Bahkan jika itu bekerja pada sistem Anda ketika Anda menjalankannya, itu mungkin tidak berfungsi ketika dijalankan di lingkungan khusus seperti cron.

robert
sumber
6
Nah, semi-portable. Pada beberapa platform, platform.node () memberikan fqdn dan yang lainnya, hanya hostname
raindog308
3
python -m timeit "import socket; socket.gethostname()" 10000 loops, best of 3: 76.3 usec per loop
Di bawah Radar
8
python -m timeit "import platform; platform.node()" 1000000 loops, best of 3: 0.74 usec per loop
Di bawah Radar
7
@BelowtheRadar jangan khawatir, saya biasanya hanya memanggil salah satu dari ini sekali per skrip.
robert
6
platform.node () bahkan lebih cepat daripada os.getenv. gethostname bahkan bukan pesaing. Tetapi jika waktu bukan faktor: import os, platform; os.getenv('HOSTNAME', os.getenv('COMPUTERNAME', platform.node())).split('.')[0]harus lintas-platform dan mendukung variabel lingkungan jika ada - yang memungkinkan beberapa kontrol pengguna dalam keadaan darurat, misalnyaHOSTNAME=correct python xyz.py
Orwellophile
121

Anda mungkin akan memuat modul os, jadi saran lain adalah:

import os
myhost = os.uname()[1]
mike0042
sumber
8
+1 untuk solusi menggunakan osmodul. Tidak portabel dan tidak terlalu akurat, tapi tetap berguna.
MestreLion
20
os.uname tidak didukung di Windows: docs.python.org/dev/library/os#os.uname
Noam Manos
9
Anda juga dapat melakukan os.uname () .nama nama untuk membuatnya sedikit lebih jelas dalam 3,3+
Hut8
4
Jawaban di bawah ini memberikan tampilan yang mirip platform.uname()[1], yang TIDAK bekerja pada Windows.
fantabolous
6
@fantabolous Anda mungkin tidak boleh menggunakan kata-kata posisi seperti "di bawah" karena jawaban mungkin telah berubah saat mendarat;)
Jonathan Komar
65

Bagaimana dengan :

import platform

h = platform.uname()[1]

Sebenarnya Anda mungkin ingin melihat semua hasilnya platform.uname()

Lucien Hercaud
sumber
1
Bekerja di Ubuntu dan Windows untuk saya. Terima kasih! 👍
GollyJer
61

os.getenv('HOSTNAME')dan os.environ['HOSTNAME']tidak selalu berhasil. Dalam pekerjaan cron dan WSDL, HTTP HOSTNAME tidak disetel. Gunakan ini sebagai gantinya:

import socket
socket.gethostbyaddr(socket.gethostname())[0]

Selalu (bahkan di Windows) mengembalikan nama host yang sepenuhnya memenuhi syarat, bahkan jika Anda mendefinisikan alias pendek di / etc / hosts .

Jika Anda mendefinisikan alias di / etc / hosts maka socket.gethostname()akan mengembalikan alias. platform.uname()[1]melakukan hal yang sama.

Saya menemukan sebuah kasus di mana hal di atas tidak berhasil. Inilah yang saya gunakan sekarang:

import socket
if socket.gethostname().find('.')>=0:
    name=socket.gethostname()
else:
    name=socket.gethostbyaddr(socket.gethostname())[0]

Pertama-tama panggilan gethostname untuk melihat apakah ia mengembalikan sesuatu yang terlihat seperti nama host, jika tidak menggunakan solusi asli saya.

Tom Ekberg
sumber
15
Anda mungkin ingin socket.getfqdn(), meskipun itu bukan apa yang diminta OP
jfs
17

Jika saya benar, Anda mencari fungsi socket.gethostname:

>> import socket
>> socket.gethostname()
'terminus'
ujung
sumber
13

Dari setidaknya python> = 3.3 :

Anda bisa menggunakan bidang nodenamedan menghindari menggunakan pengindeksan array:

os.uname().nodename

Meskipun, bahkan dokumentasi os.uname menyarankan menggunakansocket.gethostname()

Shubham Chaudhary
sumber
11

socket.gethostname() bisa melakukan

vpit3833
sumber
5

Pada beberapa sistem, nama host diatur di lingkungan. Jika itu yang terjadi pada Anda, modul os dapat menariknya keluar dari lingkungan melalui os.getenv . Misalnya, jika HOSTNAME adalah variabel lingkungan yang berisi apa yang Anda inginkan, berikut ini akan mendapatkannya:

import os
system_name = os.getenv('HOSTNAME')

Pembaruan: Seperti disebutkan dalam komentar, ini tidak selalu berhasil, karena tidak semua lingkungan diatur dengan cara ini. Saya percaya bahwa pada saat saya menjawab ini pada awalnya saya menggunakan solusi ini karena itu adalah hal pertama yang saya temukan dalam pencarian web dan itu bekerja untuk saya pada saat itu. Karena kurangnya portabilitas saya mungkin tidak akan menggunakan ini sekarang. Namun, saya meninggalkan jawaban ini untuk tujuan referensi. FWIW, itu menghilangkan kebutuhan untuk impor lain jika lingkungan Anda memiliki nama sistem dan Anda sudah mengimpor modul os. Uji - jika tidak bekerja di semua lingkungan di mana Anda mengharapkan program Anda untuk beroperasi, gunakan salah satu solusi lain yang disediakan.

GreenMatt
sumber
5
Itu mengembalikan "Tidak ada" bagi saya. Menurut tautan yang Anda poskan, itu berarti variabel 'HOSTNAME' tidak ada ...: - /
John
@ John: Apakah Anda menggunakan Windows? Ini bekerja untuk saya di kotak Linux, tapi saya juga tidak mendapatkan Windows.
GreenMatt
@MuhiaNJoroge: Saya pikir itu tergantung pada implementasi / instalasi Anda. Ketika saya menulis jawaban itu saya berada di kotak Red Hat dan itu berhasil. Sekarang saya di Ubuntu dan tidak berfungsi. Saya telah memodifikasi jawabannya.
GreenMatt
Tidak bekerja di lenovo NAS, kembali Tidak ada. Sekarang saya menggunakan impor socket print (socket.gethostname ())
Rui Martins
@RuiMartins: Seperti yang saya katakan, sepertinya tidak berfungsi di mana-mana. Senang Anda menemukan sesuatu yang berfungsi.
GreenMatt
5

Saya membutuhkan nama PC untuk digunakan dalam file conf PyLog saya, dan perpustakaan socket tidak tersedia, tetapi os library.

Untuk Windows saya menggunakan:

os.getenv('COMPUTERNAME', 'defaultValue')

Di mana DefaultValue adalah string untuk mencegah Tidak ada yang dikembalikan

Bill Kidd
sumber
12
COMPUTERNAME adalah variabel lingkungan yang sangat Microsoft dan karenanya tidak portabel.
Dwight Spencer
1
Ya, tapi itu berfungsi untuk sistem MS, dan jika cocok, itu berfungsi. Banyak kali orang di sini menjadi terlalu terikat pada kecepatan atau kemandirian platform ketika kepraktisan dan pertanyaan membuat mereka tidak relevan.
Bill Kidd
7
@BillKidd OP menyebutkan Windows, OS X, dan Linux dalam pertanyaan, jadi memerlukan portabilitas sistem adalah asumsi yang sangat masuk akal.
zstewart
1
@ BillKidd Sementara secara umum memang benar bahwa Anda harus menghindari optimasi prematur atau portabilitas, tidak menggunakan solusi yang tersedia dan dan bisa dibilang lebih dapat dipertahankan karena lebih portabel akan pergi ke ekstrim yang berlawanan.
Fisikawan Gila
2

Anda harus mengeksekusi baris kode ini

sock_name = socket.gethostname()

Dan kemudian Anda dapat menggunakan nama untuk menemukan addr:

print(socket.gethostbyname(sock_name))
Parzifal Kali
sumber