2011-12-17 21 views
4

我看起来像这样的方法:如何抛出一个异常并添加我自己的消息中包含一个键和一个值?

public IDictionary<string, string> Delete(Account account) 
{ 
    try { _accountRepository.Delete(account); } 
    catch { _errors.Add("", "Error when deleting account"); } 
    return _errors; 
} 

public IDictionary<string, string> ValidateNoDuplicate(Account ac) 
{ 
    var accounts = GetAccounts(ac.PartitionKey); 
    if (accounts.Any(b => b.Title.Equals(ac.Title) && 
          !b.RowKey.Equals(ac.RowKey))) 
     _errors.Add("Account.Title", "Duplicate"); 
    return _errors; 
} 

我想改变这个方法,让它返回一个布尔值,因此,如果有错误,而不是抛出一个异常:

_errors.Add("", "Error when deleting account"); 

有人可以向我解释我如何抛出一个异常并传递一个包含一个键和一个值的消息。在这种情况下,密钥将是"",值将是"Error when deleting account"

也在调用此方法。我将如何捕捉异常?

是否有必要让我自己创建类并以某种方式抛出基于此类的异常?

+0

_errors是什么类型? – 2011-12-17 07:13:49

+0

private Dictionary _errors; – 2011-12-17 07:28:32

回答

5

创建自己的异常类,可以保存数据,您需要:

public class AccountException : ApplicationException { 

    public Dictionary<string, string> Errors { get; set; }; 

    public AccountException(Exception ex) : base(ex) { 
    Errors = new Dictionary<string, string>(); 
    } 

    public AccountException() : this(null) {} 

} 

在你的方法,你可以抛出异常。不要返回错误状态,这是由异常处理的。

不要抛弃您在该方法中得到的异常,将其包含为InnerException,以便它可用于调试。

public void Delete(Account account) { 
    try { 
    _accountRepository.Delete(account); 
    } catch(Exception ex) { 
    AccountException a = new AccountException(ex); 
    a.Errors.Add("", "Error when deleting account"); 
    throw a; 
    } 
} 

public void ValidateNoDuplicate(Account ac) { 
    var accounts = GetAccounts(ac.PartitionKey); 
    if (accounts.Any(b => b.Title.Equals(ac.Title) && 
          !b.RowKey.Equals(ac.RowKey))) { 
    AccountException a = new AccountException(); 
    a.Errors.Add("Account.Title", "Duplicate"); 
    throw a; 
    } 
} 

当调用方法,你发现你的异常类型:

try { 
    Delete(account); 
} catch(AccountException ex) { 
    // Handle the exception here. 
    // The ex.Errors property contains the string pairs. 
    // The ex.InnerException contains the actual exception 
} 
1

创建您自己的异常,然后抛出它。

public class RepositoryException : Exception 
{ 
    public RepositoryException() : base() 
    { 
    } 

    public RepositoryException(string key, string value) : base() 
    { 
     base.Data.Add(key, value); 
    } 

    public RepositoryException(string message) : base(message) 
    { 
    } 

    public RepositoryException(string message, Exception innerException) : base(message, innerException) 
    { 
    } 
} 


public Boolean Delete(Account account) 
{ 
    try 
    { 
     _accountRepository.Delete(account); 
     return true; 
    } 
    catch (Exception ex) 
    { 
     throw new RepositoryException("", "Error when deleting account");    
     // throw new RepositoryException("Error when deleting account", ex); 
     // OR just 
     // throw new RepositoryException("Error when deleting account"); 
    } 
} 
5

Exception类有一个Data属性是键/值对的字典。

IDictionary<string, string> errors; 
... 

if (errors.Count > 0) 
{ 
    Exception ex = ... construct exception of the appropriate type 
    foreach(string key in _errors.Keys) 
    { 
     ex.Data.Add(key, _errors[key]); 
    } 
    throw ex; 
} 

注意,它通常被认为是使用可序列,让你把数据字典中的对象也应该是可序列化异常好的做法。在你的例子中,你只是把字符串,所以你会没事的。

是否有必要让我自己创建类并以某种方式抛出基于此类的异常?

肯定不是必要创建您自己的自定义Exception类,可能并不理想。 MSDN design guidelines for Exceptions给出了关于choosing which Exception type to throw的指导原则。

一般而言,除非您有一个错误条件,它可以通过与现有的异常类型不同的方式以编程方式处理,否则您应该更喜欢使用现有的异常类型之一。

1

你可以扔掉,而不是

_errors.Add("", "Error when deleting account");

所以每_errors.Add(..)自己的异常会的东西来代替像

throw new MyAppException(key, value);

如何创建自己的异常类如上所述。因此,您提供您的例外对象

你应该知道你要去哪个异常类型捕捉

try { 
    Delete(account); 
} catch(NullPointerException ex) { 
    throw new MyAppException(key, value); 
} 
在您的来电者的方法(外的方法)

现在你可以赶上只有你例外。

try { 
    _accountRepository.Delete(account); 
} catch(MyAppException ex) { 
    //exception handle logic 
} 
相关问题