a
    DøgÊ  ã                   @   s8   d dl mZ d dlmZ G dd„ dƒZG dd„ dƒZdS )é    )Údefaultdict)Úimport_modulec                   @   s    e Zd ZdZdd„ Zdd„ ZdS )ÚBlockDefinitionLookupaÒ  
    A utility for constructing StreamField Block objects in migrations, starting from
    a compact representation that avoids repeating the same definition whenever a
    block is re-used in multiple places over the block definition tree.

    The underlying data is a dict of block definitions, such as:
    ```
    {
        0: ("wagtail.blocks.CharBlock", [], {"required": True}),
        1: ("wagtail.blocks.RichTextBlock", [], {}),
        2: ("wagtail.blocks.StreamBlock", [
            [
                ("heading", 0),
                ("paragraph", 1),
            ],
        ], {}),
    }
    ```

    where each definition is a tuple of (module_path, args, kwargs) similar to that
    returned by `deconstruct` - with the difference that any block objects appearing
    in args / kwargs may be substituted with an index into the lookup table that
    points to that block's definition. Any block class that wants to support such
    substitutions should implement a static/class method
    `construct_from_lookup(lookup, *args, **kwargs)`, where `lookup` is
    the `BlockDefinitionLookup` instance. The method should return a block instance
    constructed from the provided arguments (after performing any lookups).
    c                 C   s   || _ i | _d S ©N)ÚblocksÚblock_classes)Úselfr   © r	   ú_/var/www/lab.imftr.de/x/nb_venv/lib/python3.9/site-packages/wagtail/blocks/definition_lookup.pyÚ__init__#   s    zBlockDefinitionLookup.__init__c           	      C   sv   | j | \}}}z| j| }W n> ty\   | dd¡\}}t|ƒ}t||ƒ }| j|< Y n0 |j| g|¢R i |¤ŽS )NÚ.é   )r   r   ÚKeyErrorÚrsplitr   ÚgetattrZconstruct_from_lookup)	r   ÚindexÚpathÚargsÚkwargsÚclsÚmodule_nameÚ
class_nameÚmoduler	   r	   r
   Ú	get_block'   s    zBlockDefinitionLookup.get_blockN)Ú__name__Ú
__module__Ú__qualname__Ú__doc__r   r   r	   r	   r	   r
   r      s   r   c                   @   s(   e Zd ZdZdd„ Zdd„ Zdd„ ZdS )	ÚBlockDefinitionLookupBuilderzO
    Helper for constructing the lookup data used by BlockDefinitionLookup
    c                 C   s   g | _ ttƒ| _d S r   )r   r   ÚlistÚblock_indexes_by_type©r   r	   r	   r
   r   8   s    z%BlockDefinitionLookupBuilder.__init__c                 C   s^   |  | ¡}| j|d  }|D ]\}}||kr|  S qt| jƒ}| j |¡ | ||f¡ |S )ze
        Add a block to the lookup table, returning an index that can be used to refer to it
        r   )Zdeconstruct_with_lookupr    Úlenr   Úappend)r   ÚblockZdeconstructedZblock_indexesr   Zexisting_deconstructedr	   r	   r
   Ú	add_blockB   s    


z&BlockDefinitionLookupBuilder.add_blockc                 C   s   t t| jƒƒS r   )ÚdictÚ	enumerater   r!   r	   r	   r
   Úget_lookup_as_dictT   s    z/BlockDefinitionLookupBuilder.get_lookup_as_dictN)r   r   r   r   r   r%   r(   r	   r	   r	   r
   r   3   s   
r   N)Úcollectionsr   Ú	importlibr   r   r   r	   r	   r	   r
   Ú<module>   s   .