Jak utworzyć listę drukarek sieciowych dostępnych dla zalogowanego użytkownika?
Skrypciarze odpowiadają na Wasze pytania
Witamy w rubryce TechNet, w której Skrypciarze z firmy Microsoft odpowiadają na częste pytania dotyczące używania skryptów w administracji systemu. Jeśli macie jakieś pytania z tej dziedziny, zachęcamy do wysłania e-maila na adres: scripter@microsoft.com. Nie możemy zagwarantować odpowiedzi na każde otrzymane pytanie, ale staramy się jak możemy. |
Jak utworzyć listę drukarek sieciowych dostępnych dla zalogowanego użytkownika?
Cześć, Skrypciarze! Jak utworzyć skrypt logowania tworzący listę drukarek sieciowych dostępnych dla zalogowanego użytkownika i zapisujący te informacje w pliku tekstowym?
-- RC
Cześć, RC! Najfajniejszą rzeczą po powrocie do pracy z weekendu czy wakacji jest… rety, nic nie przychodzi mi do głowy i w sumie nie wiem, co może być chociaż trochę fajnego po powrocie z urlopu. Nawet mój talent pisarski zawodzi w obliczu czegoś tak potwornego, powrót z weekendu czy urlopu. Chociaż inni mają pewnie gorzej, bo ja po wakacjach wracam zawsze do firmy Microsoft, a tam chociaż dokarmiam się intelektualnie i lingwistycznie, podsłuchując rozmowy kolegów i koleżanek. Taką na przykład rozmowę usłyszałem (broń Boże nie podsłuchałem) dziś w toalecie:
-No to jak to się stało, ze dostał gabinet z oknem?
-No musiałem mu dać. Powiedział, ze bez okna robi się nerwowy, a nawet może dostać ataku furii (nie padł przy tym ani jeden wulgaryzm – przyp.aut.). Nie chciałem żeby wpadał we wściekłość, więc musiałem mu dać to okno, no nie?
Nie trzeba chyba nadmieniać, że pokoje z oknem są w biurowcu najcenniejszym towarem i przydzielane są tylko najlepszym i najbystrzejszym (oraz naszej Skrypciarskiej Redaktorce). Tylko że nie wiedzieć czemu autor niniejszego artykułu siedzi teraz za biurkiem w pokoju bez okna… Może dlatego, że ukrywa się pod bardzo zmyślnym pseudonimem i mało kto zna jego prawdziwe imię. Może też dlatego, ze nigdy jeszcze nie zagroził nikomu, że bez okna dostanie ataku szału. Czas się nad tym zastanowić i wymyślić jakiś ciekawy napad, bo może za pomysłowy atak można dostać nawet dwa okna.
Tylko, że w żadnym wypadku atak szału. Na przemoc biurową trzeba być przynajmniej nierozleniwionym, czego nie można powiedzieć o piszącej to osobie, a na atak frustracji się nie nadajemy, ponieważ czujemy się w 100% spełnieni, mogąc napisać skrypt logowania tworzący listę drukarek sieciowych dostępnych dla zalogowanego użytkownika:
Const ForWriting = 2
Set objNetwork = CreateObject("Wscript.Network")
strName = objNetwork.UserName
strDomain = objNetwork.UserDomain
strUser = strDomain & "\" & strName
strText = strUser & vbCrLf
strComputer = "."
Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")
Set colPrinters = objWMIService.ExecQuery _
("Select * From Win32_Printer Where Local = FALSE")
For Each objPrinter in colPrinters
strText = strText & objPrinter.Name & vbCrLf
Next
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objFile = objFSO.CreateTextFile _
("C:\Scripts\Printers.txt", ForWriting, True)
objFile.Write strText
objFile.Close
Dwie uwagi, zanim przejdę do objaśniania, na jakiej zasadzie działa nasz skrypt. Więc po pierwsze primo, nie zadziała na pewno ani w systemie Windows 2000, ani w żadnej wcześniejszej wersji. Dzieje się dlatego, że w tych wersjach systemu Windows klasa WMI Win32_Printer nie zawiera właściwości Local. Nie wpadajcie w szał – pokażemy także skrypt, który zadziała w starszych wersjach Windows.
Po drugie primo (wiem, wiem, że tak się nie mówi, ale może redakcja dojdzie do wniosku, że tracę zmysły robiąc tak poważne błędy językowe jak „po pierwsze primo”, nie mówiąc już o „po drugie primo”), powyższy skrypt zapisuje informację w pliku tekstowym o nazwie C:\Scripts\Printers.txt; każde uruchomienie skryptu powoduje zastąpienie zawartości pliku printers.txt najbardziej aktualną kolekcją informacji o drukarkach. Wszystko OK, ale być może nie o to chodziło. Jeśli tak, to konieczne będzie zmodyfikowanie kodu tworzącego zapisy do pliku tekstowego.
Teraz już możemy zabrać się za tłumaczenie, jak działa nasz dzisiejszy skrypt. Najpierw definiujemy stałą o nazwie ForWriting i ustawiamy jej wartość na 2; będziemy z niej korzystać podczas zapisywania informacji o drukarce do pliku tekstowego. Następnie tworzymy wystąpienie obiektu Wscript.Network i uruchamiamy poniższe trzy wiersze kodu:
strName = objNetwork.UserName
strDomain = objNetwork.UserDomain
strUser = strDomain & "\" & strName
W pierwszych dwóch wierszach ustalamy nazwę zalogowanego użytkownika (używamy przy tym właściwości UserName) oraz jego domenę (właściwość UserDomain). W trzecim wierszu natomiast łączymy nazwę użytkownika z domeną, podając nazwę użytkownika w formacie DOMAIN\username. Innymi słowy:
FABRIKAM\kenmyer
Następnie dołączamy do tych informacji znak powrotu karetki (używając do tego stałej vbCrLf języka VBScript) i przechowujemy je w zmiennej o nazwie strText:
strText = strUser & vbCrLf
Łączymy się potem z usługą WMI na komputerze lokalnym (z uwagi na to, ze jest to skrypt logowania, nie musimy się martwić o łączenie z usługą WMI na komputerze zdalnym). Następnie, używając poniższych wierszy kodu, pobieramy kolekcję wszystkich drukarek sieciowych dla danego komputera:
Set colPrinters = objWMIService.ExecQuery _
("Select * From Win32_Printer Where Local = FALSE")
Wybieramy tutaj wystąpienia klasy Win32_Printer lub przynajmniej wystąpienia, których właściwość Local ustawiona jest na False. Wynik naszej operacji jest następujący: jeżeli właściwość Local miała wartość True, mamy do czynienia z drukarką lokalną, a nie sieciową. Dlatego też skrypt nie działa dla programu Windows 2000 – klasa Win32_Printer w programie Windows 2000 nie zawiera właściwości Local.
Nie martwcie się jednak, a pod żadnym pozorem nie wpadajcie we wściekłość (szczególnie jeżeli siedzicie w pokoju bez okien), obiecaliśmy przecież, że można wyjść z tego impasu lokalnego.
Zanim jednak zdradzimy, jak to zrobić, skończmy najpierw objaśnianie skryptu wyjściowego. Po pobraniu informacji na temat drukarki uruchamiamy pętlę, która przechodzi przez całą kolekcję. Dla każdej drukarki w kolekcji używamy poniższego wiersza kodu i dodajemy nazwę (Name) drukarki do zmiennej strText:
strText = strText & objPrinter.Name & vbCrLf
Dzięki temu przypisujemy zmiennej strText nową wartość, która jest niczym innym, jak tylko istniejącą wartością strText, do której dodajemy nazwę drukarki oraz znak powrotu karetki.
Reszta to betka. Najpierw tworzymy wystąpienie obiektu Scripting.FileSystemObject, następnie korzystając z metody CreateTextFile, tworzymy nowy plik tekstowy o nazwie C:\Scripts\Printers.txt:
Set objFile = objFSO.CreateTextFile _
("C:\Scripts\Printers.txt", ForWriting, True)
Należy zwrócić uwagę na trzy parametry przekazywane metodzie CreateTextFile method:
• | Kompletna ścieżka (C:\Scripts\Printers.txt). |
• | Stała ForWriting, która wskazuje na to, że chcemy dokonać zapisu w pliku. |
• | Wartośc True, która instruuje skrypt, aby zastąpił istniejące wystąpienia C:\Scripts\Printers.txt. Jeżeli plik Printers.txt istnieje, skrypt go zastąpi, jeżeli jeszcze nie istnieje, nasz skrypt go dopiero utworzy |
Następnie przywołujemy metodę Write i zapisujemy informację na temat drukarki do pliku, po czym używając metody Close zamykamy plik. Podczas otwierania pliku tekstowego powinniśmy zobaczyć taką informację:
FABRIKAM\kenmyer
\\atl-ps-01\b43-2927-a
\\atl-ps-01.fabrikam.com\b43-2315-a
\\atl-ps-02\HP LaserJet 5MP
Właśnie to chcielismy zobaczyć.
Co z systemem Windows 2000? Oto skrypt logowania, który będzie działał w wersji 2000 oraz Windows NT:
Const ForWriting = 2
strComputer = "."
Set objNetwork = CreateObject("Wscript.Network")
strName = objNetwork.UserName
strDomain = objNetwork.UserDomain
strUser = strDomain & "\" & strName
Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")
strText = strUser & vbCrLf
Set colPrinters = objWMIService.ExecQuery("Select * From Win32_Printer")
For Each objPrinter in colPrinters
If Not objPrinter.Attributes And 64 Then
strText = strText & objPrinter.Name & vbCrLf
End If
Next
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objFile = objFSO.CreateTextFile _
("C:\Scripts\Printers.txt", ForWriting, True)
objFile.Write strText
objFile.Close
Jaka jest różnica między skryptami? Tym razem musimy zwrócić wszystkie drukarki, zarówno lokalne, jak i sieciowe. Następnie sprawdzamy wartość właściwości typu maska bitów Attributes. Jeśli przełącznik o wartości 64 jest włączony, oznacza to, że chodzi o drukarkę lokalną. W przeciwnym razie musi to być drukarka sieciowa. W takim wypadku dodajemy właściwość Name drukarki do zmiennej strText.
Zanim jednak skończę, dodam, że po przemyśleniu dochodzę do wniosku, że pierwotna teza, iż pokoje z oknem przydzielane są tylko najlepszym i najbystrzejszym nie może być prawdziwa, bo nie ma innej opcji – pokój z największą liczbą okien musiałbym dostać ja. Przypuszczam, że chodzi tu tylko i wyłącznie o wiek i że nasza skrypciarska Redaktorka dostała tak lukratywny przydział nie z uwagi na to, że uważa się ją za bardzo, bardzo bystrą, a raczej bardzo, bardzo podeszłą w wieku (nie wypada napisać starą przecież).
Nie mówcie jej tylko o tym!
Uwaga od Redaktorki: Byłam w dziale personalnym i autor powyższych wypocin jest znacznie starszy od redaktorki, więc obala to chyba teorię o wieku... Ale więcej nic nie powiem, bo jeszcze by zrozumiał aluzję. |
Do początku strony |