Skip to main content

Mate -- налаживаем отладку (отлаживаем наладку)

Posted in

Кто следит за моим микроблогом в жуйке мог сегодня наблюдать, как я отчаянно боролся за правильную отладку с Mate. Благодаря неравнодушным товарищам проблему удалось одолеть. Делюсь решением.

Но сперва, а в чем, собственно проблема? Дело в том, что наши проекты в основном многопользовательские. И часто они отлаживаются не из дебаггера в IDE, а просто в браузере. Потому что нужно запустить несколько экземпляров приложения от разных пользователей и проверить взаимодействие пользователей.

Мы пользуемся собственным тулом, принимающим отладочные сообщения из приложений по LocalConnection. Нечно вроде De Monster Debugger, но чутка другой. Фишка в том, что наш тул показывает то, что передано нашему статическому методу Debug.Trace(), но не показывает то, что передано стандартному trace(). Который, к великому моему сожалению, переопределить нельзя. haXe программисты радуются -- им это можно :)

А вот Mate фреймворк все свои сообщения выбрасывает с помощью trace. Их видно при отладке в IDE, но не видно при отладке в браузере. И это было бы небольшой проблемой, если бы не один случай.

Был такой код:

<mate:EventHandlers type="{RoomEvent.LEAVE}" debug="true">
	<mate:MethodInvoker generator="{MainChatManager}"
		method="LeaveRoom" arguments="{[event.room]}"/>
</mate:EventHandlers>

Который обрабатывался как-то так:

public function LeaveRoom(room : RoomVO) : void
{
	// do something
}

Потом RoomEvent был отрефакторен так, что содержал не RoomVO а roomID : String. При этом код в карте не был исправлен. Ну не большая беда -- сгенерится исключение, увидим, поправим.

Но в том-то и беда, что исключения я не увидел. Mate его перехватил и выдал инфу в trace(), так что я ничего не увидел. А проблему диагносцировал по побочным эффектам из-за невызванного метода LeaveRoom.

Вот тут я и понял, что так жить нельзя. Сами понимаете, побочные эффекты можно и не увидеть, или увидеть такие, что по ним хрен чего поймешь. Нужно видеть исключение.

К счастью быстро выяснилось, что Mate не просто тупо валит инфу в trace(), а использует logging API. Стало быть, к нему можно подключить свою реализацию AbstractTarget, получать эту инфу и бросать в свой дебаг.

К несчастью также выяснилось, что в Mate этот logging используется нестандартно, причем ничего на этот счет не документировано. Так что пришлось лезть в сорцы.

В итоге, вот работающее решение:

MateLogTarget

/**
 * @author Yura Zhloba
 */
package com.flashdevs.debug
{
import com.asfusion.mate.events.MateLogEvent;
import com.asfusion.mate.utils.debug.DebuggerHelper;

import mx.logging.LogEvent;
import mx.logging.LogEventLevel;
import mx.logging.targets.LineFormattedTarget;

public class MateLogTarget extends LineFormattedTarget
{
	// properties
	private var helper : DebuggerHelper = null;

	// constructor
	public function MateLogTarget()
	{
		filters = ["*"];
		level = LogEventLevel.ALL;
		includeDate = true;
		includeTime = true;
		includeCategory = true;
		includeLevel = true;
	}

	// methods
	public override function logEvent(event : LogEvent) : void
	{
		super.logEvent(event);
		var msg : String = event.message;

		if(event is MateLogEvent)
		{
			if(helper == null) helper = new DebuggerHelper();
			msg = helper.getMessage(event);
		}

		trace(msg);
		Debug.Trace(msg);
	}

	public function toString() : String
	{ return 'MateLogTarget'; }
}
}

Debug

public class Debug
{
	// static methods
	static public function Trace(input : *, type : * = null) : void
	{
		// send data through LocalConnection
	}

	static public function InitMateLogTarget() : void
	{
		var target : MateLogTarget = new MateLogTarget();
		Log.addTarget(target);
		MateManager.instance.debugger = target;
	}
}
}

MainEventMap

<mate:EventHandlers type="{FlexEvent.CREATION_COMPLETE}">
	<mate:InlineInvoker method="Debug.InitMateLogTarget" />
	<!-- do something esle -->
</mate:EventHandlers>

Теперь все ок, я вижу все сообщения Mate и при отладке в IDE, и при отладке в браузере.

No votes yet