Magento - search for a block matching an HTML fragment

I am new to Magento, and one of the things that I find inconvenient when studying the system is to bind a given element on the generated (X) HTML page to the name of the created block. I know System-> Configuration-> template path hints. However, it is very ugly, sometimes it changes the arrangement of elements on the page and does not display all the blocks (I think that it covers only blocks of templates).

The approach I tried is to change the toHtml() method in Mage_Core_Block_Abstract to add empty elements before and after the content, for example.

 <blockStart xmlns="http://some/url" name="the_block_name"/> <!-- the block contents --> <blockEnd/> 

(There may be a way to do this without modifying the kernel files, but at the moment I am not opposed to this approach, since it is only for my own use. However, any ideas are welcome.)

These elements give me enough information in the document to use the browser side jQuery .nextUntil() function to add data-magento-blockname to the elements between the blockStart and blockEnd elements. Then I can use these attributes to display a tooltip containing the full name of the "path" block to the content under the pointer at any given time.

The problem with this approach is that although Magento creates XHTML with strict DOCTYPE, it rigidly sets the Content-Type to "text / html" (see app/code/core/Mage/Core/Model/App.php line 1246 ) This means that the XML is interpreted by the browser as an β€œHTML soup tag”, which leads to strange things - many of my tags disappear altogether, appear in the wrong places, or don’t close right away, so they contain different content. Also, not all HTML elements in a document are displayed in the DOM.

I tried modifying App.php to change the Content-Type to application / xhtml + xml, and this allows my mechanism to work successfully. However, it has some serious flaws:

  • I had to disable add-ons, in particular Commerce Bug, which do not produce valid XHTML. Losing Commerce Bug is pretty bad, since I really want to access my page and batch XML viewer functions while my add-in is working.
  • Most of the javascript included in Magento uses document.write (), which does not work with XHTML, so I get javascript exceptions and, apparently, some functions do not work.

Does anyone know of any solutions to these problems with my approach or know of some easier way to link the HTML elements in the output to the Magento blocks that produce them?

+4
source share
2 answers

Update . It ended up taking some time, but finally I give you BlockSpy: http://omnicognate.wordpress.com/2012/11/13/blockspy-my-first-magento-extension/


Refresh I did not have much time to work on this, but now I have the server part of this work. By adding blockStart / blockEnd markers to the core_block_abstract_to_html_after event handler, I managed to do this without changing any main files, and putting them in the comments, I got them to go through HTMLTidy without any problems. The SAX analyzer bit is working. There's just a javascript client bit that should be simple - the idea is to do something in the style of XRAY CSS bookmarks (http://westciv.com/xray/).

I will refer to the article on how it works, update and accept this answer when it is done - unless someone else has come up with a better solution earlier, of course.


I think I am closing the decision. It seems the problem really comes down to 3 things:

  • Magento really does not create reliable XHTML. For example, there is some inconsistency in the use of CDATA partitions for Javascript. I came across several invalid pages, and undoubtedly more of them.
  • Page generation is done in a purely textual way. Because the server manipulates strings rather than the DOM, it is not easy to reliably insert markup on the server side. In addition, AFAIK does not guarantee that toHtml() block methods will always create collections of integer elements. For example, there is nothing that would stop you (I think) from having a block that creates the text and embeds it inside the attribute value in the parent block, or to open the XHTML element in the parent block and close it in the child element (although this is grim) .
  • Switching Content-Type to XHTML, even if the server is convinced of the correct correct markup, completely breaks the javascript on the site, and I'm not ready to go through it and update everything to work with XHTML.

I think the following approach can solve these problems:

  • Use PHP::Tidy on the server side to force the server to create valid XHTML. I tried running tidy_parse_string() in the controller_front_send_response_before handler and it seems to work.
  • Instead of the blockStart / blockEnd tokens that are inserted into the class of the Block class being processed on the client side, use the server-side SAX XML parser to process the response before sending it. I can run substrings between the markers, passing each substring to the SAX parser when I go (and leave the markers). This should allow me to maintain state and create an XML output string in response to the events that the SAX parser generates. Then I can insert the data- * attributes safely (if slowly) on the server side.
  • Leave the Content-Type as text / html. This will allow javascript to work, and the data- * attributes will be ignored on the client side if you want.

A bit of a pain, but it looks like it should work with all my extensions, not break javascript and avoid making any assumptions about what output the block produces. I just tried the first step - it will be updated as soon as I have a crack in the complex bit :-)

+1
source

When using path template hints, sometimes you need to check an element, and then find the associated template file specified when viewed in ChromeDevTools or Firebug (this will be the parent element with a bunch of inline styles).

I often use grep to find things. Just go to the highest folder where you think you should search (so as not to go through thousands of unrelated folders / files).

So, if you know the name of the block and want to find which template files use this block, you can go to / app / design / frontend / base / default / layout and do something like:

 grep "catalog/category" -r -l . 

and you can get some file names that load this block, then find their ad nodes and see which template file is loading.

 echo get_class($this) 

May also be helpful.

+2
source

Source: https://habr.com/ru/post/1437888/


All Articles