using System;
using System.IO;
using System.Collections;
using System.Collections.Generic;
using System.Reflection;
using System.Xml.Linq;
namespace Lucene.Linq.Utility
{
public class ObjectDumper {
const ConsoleColor CIdent = ConsoleColor.Cyan;
const ConsoleColor CValue = ConsoleColor.Magenta;
public static void Write(object o) {
Write(o, 0);
}
public static void Write(object o, int depth) {
ObjectDumper dumper = new ObjectDumper(depth);
dumper.WriteObject(null, o);
}
TextWriter _writer;
int _pos;
int _level;
int _depth;
private ObjectDumper(int depth) {
this._writer = Console.Out;
this._depth = depth;
}
private void Write(string s) {
if (s != null) {
_writer.Write(s);
_pos += s.Length;
}
}
private void Write(string s, ConsoleColor c) {
ConsoleColor temp = Console.ForegroundColor;
Console.ForegroundColor = c;
Write(s);
Console.ForegroundColor = temp;
}
private void WriteIndent() {
for (int i = 0; i < _level; i++) _writer.Write(" ");
}
private void WriteLine() {
_writer.WriteLine();
_pos = 0;
}
private void WriteTab() {
Write(" ");
while (_pos % 8 != 0) Write(" ");
}
private void WriteObject(string prefix, object o) {
if (o == null || o is ValueType || o is string || o is XElement) {
WriteIndent();
Write(prefix);
WriteValue(o);
WriteLine();
} else if (o is IEnumerable) {
foreach (object element in (IEnumerable)o) {
if (element is IEnumerable && !(element is string)) {
WriteIndent();
Write(prefix);
Write("...");
WriteLine();
if (_level < _depth) {
_level++;
WriteObject(prefix, element);
_level--;
}
} else {
WriteObject(prefix, element);
}
}
} else {
MemberInfo[] members = o.GetType().GetMembers(BindingFlags.Public | BindingFlags.Instance);
WriteIndent();
Write(prefix);
bool propWritten = false;
foreach (MemberInfo m in members) {
FieldInfo f = m as FieldInfo;
PropertyInfo p = m as PropertyInfo;
if (f != null || p != null) {
if (propWritten) {
WriteTab();
} else {
propWritten = true;
}
Write(m.Name, CIdent);
Write("=");
Type t = f != null ? f.FieldType : p.PropertyType;
if (t.IsValueType || t == typeof(string)) {
WriteValue(f != null ? f.GetValue(o) : p.GetValue(o, null));
} else {
if (typeof(IEnumerable).IsAssignableFrom(t)) {
Write("...");
} else {
Write("{ }");
}
}
}
}
if (propWritten) WriteLine();
if (_level < _depth) {
foreach (MemberInfo m in members) {
FieldInfo f = m as FieldInfo;
PropertyInfo p = m as PropertyInfo;
if (f != null || p != null) {
Type t = f != null ? f.FieldType : p.PropertyType;
if (!(t.IsValueType || t == typeof(string))) {
object value = f != null ? f.GetValue(o) : p.GetValue(o, null);
if (value != null) {
_level++;
WriteObject(m.Name + ": ", value);
_level--;
}
}
}
}
}
}
}
private void WriteValue(object o) {
if (o == null) {
Write("null");
} else if (o is DateTime) {
Write(((DateTime)o).ToShortDateString(), CValue);
} else if (o is ValueType || o is string || o is XElement) {
Write(o.ToString(), CValue);
} else if (o is IEnumerable) {
Write("...");
} else {
Write("{ }");
}
}
}
}