StringBuilder ScriptTable(DataBossTable table, StringBuilder result) {
			result.Append("create table ");
			AppendTableName(result, table)
				.Append("(");
			
			table.GetColumns().ForEach(x => ScriptColumn(result, x));

			result.AppendLine();
			return result.Append(')');
		}
		StringBuilder ScriptConstraints(DataBossTable table, StringBuilder result) {
			var columns = table.GetColumns().ToList();

			var clustered = columns.Where(x => x.Any<ClusteredAttribute>())
				.Select(x => x.Name)
				.ToList();
			if(clustered.Count > 0)
				result.AppendFormat("create clustered index IX_{0}_{1} on [{0}]({2})",
					table.Name,
					string.Join("_", clustered),
					string.Join(",", clustered)
				).AppendLine();

			var keys = columns.Where(x => x.Any<KeyAttribute>())
				.Select(x => x.Name)
				.ToList();
			if(keys.Count > 0) {
				result
					.AppendFormat(result.Length == 0 ? string.Empty : Environment.NewLine)
					.AppendFormat("alter table [{0}]", table.Name)
					.AppendLine()
					.AppendFormat("add constraint PK_{0} primary key(", table.Name)
					.Append(string.Join(",", keys))
					.Append(")");
			}
			return result;
		}
		static StringBuilder AppendTableName(StringBuilder target, DataBossTable table) {
			if(!string.IsNullOrEmpty(table.Schema))
				target.AppendFormat("[{0}].", table.Schema);
			return target.AppendFormat("[{0}]" , table.Name);
		}
			public override MetaTable GetTable(Type rowType) {
				MetaTable cached;
				if(knownTables.TryGetValue(rowType, out cached))
					return cached;
				return knownTables[rowType] = new DataBossTable(this, rowType);
			}