2017-06-15 9 views
0

私はTrade(Network Security Engineer)のソフトウェアエンジニアではなく、より多くのオートメーション技術とコーディングを学んでいます。私は私のコードの中でかなり明白なものを見逃していると確信しています。IPアドレスモジュールでの例外処理

私は、入力ボックス(Tkinter内)にIPv4/v6形式のCIDRまたはホストIPのいずれかでIPアドレスを入力するように求める入力スクリプトを実行しています。私はこれらの機能(CIDRとホストIP)のそれぞれを実行する2つの別々のコーディングスクリプトを持っています。私は一緒にコードを結合しようとしているので、1つのアプリケーションだけを実行する必要があります。

ipaddressモジュールを使用している場合、入力された形式が正しくない場合(ホストアドレスの場合はip_address、CIDRアドレスの場合はip_networkを使用)、Valueエラーが発生します。私はこれらの例外を処理しているので、これが私の望むものです。

問題は、CIDRとIPホストの両方がREST API呼び出し用のリストを別々に追加する必要があることです(異なる呼び出し形式が必要なため)。私の下のコードプロセスでは、テキストボックスへの入力がCIDR形式であれば、(IPホストがエラーを投げる最初のステートメントなので)値エラーがスローされます。

私は(最初は空の入力のためだけのフェイルセーフである)、第2のelif文を置き換えるに次のコードを同時にIPアドレスの入力を処理持つことができました:

if self.ip == str(ipaddress.ip_network(self.e1.get())) or self.ip == str(ipaddress.ip_address(self.e1.get())): 

私はself.ipを解読し、それを適切なリスト(CIDRとIPホスト用)に追加する方法がないということです。

私の主なコードの主な問題は、入力がCIDRの場合、2番目のelifブロックが最初の入力としてipaddress.ip_addressを持つため、値エラーが発生することです。エラーは、コードを続行しません。

構造上の問題か、適切な質問はしません...しかし、コード内で人がホストIPアドレスまたはCIDRフォーマットのサブネットのいずれかを入力できるようにして、コードが値エラーを投げるそれらの2つのうちどれも入力されていない場合同様にそれぞれを適切なリストに追加すると、非常に感謝しています。

メインコード(FYI:E1変数は、入力テキストボックスです):ここでは

def add_ip(self): 
    self.hostiplist = [] 
    self.cidriplist = [] 
    try: 
     if not self.e1.get():# empty! (empty string is false value) 
     messagebox.showerror(title='Error', message='Ooops, Please enter an acceptible host or network IP Address.') 
     self.e1.delete(0,END) 
     elif self.e1.get() == " ": 
     messagebox.showerror(title='Error', message='Ooops, Please enter an acceptible host or network IP Address.') 
     self.e1.delete(0,END) 
     else: 
     self.ip = self.e1.get() 
     if self.ip == str(ipaddress.ip_address(self.e1.get())): 
      self.hostiplist.append(self.ip) 
      print("IP Host staged for deployment: %s" % (self.ip)) 
      print("") 
      self.e1.delete(0,END) 
     elif self.ip == str(ipaddress.ip_network(self.e1.get())): 
      self.cidriplist.append(self.ip) 
      print("IP Network staged for deployment: %s" % (self.ip)) 
      print("") 
      self.e1.delete(0,END) 
     else: 
      print("Didn't enter valid entry") 

    except ValueError as e: 
     messagebox.showerror(title='Error', message='Ooops,' + str(e) + '.' + ' Please enter an acceptible host or network IP Address.') 
     self.e1.delete(0,END) 
     return 'Value'  
    except TypeError: 
     messagebox.showerror(title='Error', message='Ooops,' + str(e) + '.' + ' Please enter an acceptible host or network IP Address.') 
     self.e1.delete(0,END) 
     return 'Type' 

は、エラーがCIDR形式以外のものが入っている場合は、値を受け取ります(取り扱いで動作します私の単一機能のスクリプトがありますエラー):よろしく

def add_ip_network(): 
    #IPv4 & v6 Address Handling. Nothing but those formats can be entered. 
    try: 
    ip = ipaddress.ip_network(e1.get()) 
    nonsubnethostsList.append(ip) 
    print("IP Network staged for deployment: %s" % (ip)) 
    print("") 
    e1.delete(0,END) 
    except ValueError: 
    print('Incorrect entry, please use IPv4 or IPv6 CIDR Formats') 
    e1.delete(0,END) 
    return 'Value' 
    except TypeError: 
    print('Incorrect entry, please use IPv4 or IPv6 CIDR Formats') 
    e1.delete(0,END) 
    return 'Type' 

編集:私はまた私の作業に合わせて、私のメインのコードを調整しようとした
単一形式のスクリプト。これに

if self.ip == str(ipaddress.ip_address(self.e1.get())) 

::このことから

ip = ipaddress.ip_network(e1.get()) 

は、それは私と同じ値のエラーを与えたので、私はただのIf文で文字列を比較しようとしました。

答えて

0

ユーザーDagger0から上記の質問に対してReddit/Pythonに関する回答がありました(感謝!)。

基本的には、文字列がIPまたはCIDRマスクのネットワークであるかどうかを確認します。あなたは "/"をテストできるようです。我々は同様かもしれないので、

# Presumably set these in __init__ or something, you don't 
# want to be clearing them each time you add an entry. 
self.hostiplist = [] 
self.cidriplist = [] 

def add_ip(self): 
    input = self.e1.get() 
    try: 
     if "/" in input: 
      ip = ipaddress.ip_address(input) 
      # Append to self.hostiplist. 
     else: 
      network = ipaddress.ip_network(input) 
      # Append to self.cidriplist. 
    except (ValueError, TypeError) as e: 
     msg = 'Ooops: %s. Please enter an acceptable host or network IP Address.' % str(e) 
     messagebox.showerror(title='Error', message=msg) 
     self.e1.delete(0, END) 
     raise e # If you want the caller to get an exception too. Although in that case maybe the 
       # whole try/except business should be in the caller, like in the bottom code block. 

(完全にテストされていない。)

私は(ipaddress.ip_address基づいて「「のチェックを削除」とは」)は、おそらく、とにかくこれらの入力で例外がスローされます1つの例外ハンドラを使用してください。それが実際にどのように動作するのかわかりません。

あなたの一般的な問題は、ipaddress.ip_address()がスローした後にipaddress.ip_network()を試しても気にしないことです(ただし、この場合は2つの入力を区別する別の方法があります)。

また、このようにそれを行うことができます:私は下の二つの機能をテストし、彼らは完璧に働い

def add_ip(self, input): 
    try: 
     ipaddress.ip_address(input) 
     # It's an IP. 
    except (ValueError, TypeError): 
     ipaddress.ip_network(input) 
     # It's a network. 

def on_button_press(self): 
    try: 
     self.add_ip(self.e1.get()) 
    except (ValueError, TypeError): 
     # Neither. 
     self.e1.delete(0, END) 

try: 
    ipaddress.ip_address(input) 
    # It's an IP. 
except (ValueError, TypeError): 
    ipaddress.ip_network(input) 
    # It's a network. 

は、おそらくこのようなコード構造につながります!これが他人を助けることを望みます。