o
    /ѹg0                     @   s   d dl Z d dlmZ d dlmZmZmZ d dlmZm	Z	m
Z
 d dlmZ ddlmZ ddlmZ e ZG d	d
 d
ZG dd dZdS )    N)Optional)GitErrorInvalidParameterNotLoginException)DEFAULT_DATASET_REVISIONDEFAULT_REPOSITORY_REVISIONMASTER_MODEL_BRANCH)
get_logger   )GitCommandWrapperget_endpointc                   @   s   e Zd ZdZeddfdededee dee dee f
dd	Zd
d Zdd Z	d%dedefddZ
defddZeedfdedee dee dee fddZefdeded ee fd!d"Zefdeded ee fd#d$ZdS )&
Repositoryz8A local representation of the model git repository.
    N	model_dir
clone_fromrevision
auth_tokengit_pathc                 C   s   || _ tj|| _tj|| _|sd}t|ddlm	} |r%|| _
n| | _
t }| s6td t|| _tj| j dd | |}	t| j r`|  }
| j|
}
|
r`|
|	kr`dS | j| j| j
|	| j| | rw|| j  | j| j| j | j
r| j| j | j
 dS dS )a"  Instantiate a Repository object by cloning the remote ModelScopeHub repo

        Args:
            model_dir (str): The model root directory.
            clone_from (str): model id in ModelScope-hub from which git clone
            revision (str, optional): revision of the model you want to clone from.
                     Can be any of a branch, tag or commit hash
            auth_token (str, optional): token obtained when calling `HubApi.login()`.
                        Usually you can safely ignore the parameter as the token is already
                        saved when you login the first time, if None, we will use saved token.
            git_path (str, optional): The git command line path, if None, we use 'git'

        Raises:
            InvalidParameter: revision is None.
        0a non-default value of revision cannot be empty.r   ModelScopeConfigz)git lfs is not installed, please install.Texist_okN)r   ospathdirnamemodel_base_dirbasenamemodel_repo_namer   modelscope.hub.apir   r   	get_tokenr   Zis_lfs_installedloggererrorgit_wrappermakedirs_get_model_id_urllistdir_get_remote_urlremove_token_from_urlcloneZgit_lfs_installadd_user_infoconfig_auth_token)selfr   r   r   r   r   err_msgr   r#   url
remote_url r0   ]/Users/admin/.pyenv/versions/3.10.0/lib/python3.10/site-packages/modelscope/hub/repository.py__init__   s@   




zRepository.__init__c                 C   s   t   d| d}|S )N/.gitr   )r,   Zmodel_idr.   r0   r0   r1   r%   P   s   zRepository._get_model_id_urlc                 C   .   z
| j | j}W |S  ty   d }Y |S w N)r#   get_repo_remote_urlr   r   r,   remoter0   r0   r1   r'   T      zRepository._get_remote_urloriginmasterr9   branchc                 C   s   | j j| j||d dS )zPull remote branch

        Args:
            remote (str, optional): The remote name. Defaults to 'origin'.
            branch (str, optional): The remote branch. Defaults to 'master'.
        )r9   r=   N)r#   pullr   )r,   r9   r=   r0   r0   r1   r>   [   s   zRepository.pullfile_name_suffixc                 C   s"   t d|t j| jdf  dS )zAdd file suffix to lfs list.

        Args:
            file_name_suffix (str): The file name suffix.
                examples '*.safetensors'
        z5printf '
%s filter=lfs diff=lfs merge=lfs -text
'>>%sz.gitattributesN)r   systemr   joinr   )r,   r?   r0   r0   r1   add_lfs_typed   s
   zRepository.add_lfs_typeFcommit_messagelocal_branchremote_branchforcec                 C   s   |du s	t |tsd}t|t |tstd| jstd| j| j| j | j	| j
| j | j| j}| jj| jdd | j| j| | jj| j| j|||d dS )a  Push local files to remote, this method will do.
        Execute git pull, git add, git commit, git push in order.

        Args:
            commit_message (str): commit message
            local_branch(str, optional): The local branch, default master.
            remote_branch (str, optional): The remote branch to push, default master.
            force (bool, optional): whether to use forced-push.

        Raises:
            InvalidParameter: no commit message.
            NotLoginException: no auth token.
        N commit_message must be provided!force must be bool'Must login to push, please login first.T	all_filesrepo_dirtokenr.   rD   rE   )
isinstancestrr   boolr   r   r#   r+   r   r*   r   r   r7   addcommitpush)r,   rC   rD   rE   rF   msgr.   r0   r0   r1   rT   o   s*   


zRepository.pushtag_namemessagerefc                 C   sR   |du s|dkrd}t ||du s|dkrd}t || jj| j|||d dS )a  Create a new tag.

        Args:
            tag_name (str): The name of the tag
            message (str): The tag message.
            ref (str, optional): The tag reference, can be commit id or branch.

        Raises:
            InvalidParameter: no commit message.
        N zFWe use tag-based revision, therefore tag_name cannot be None or empty.z=We use annotated tag, therefore message cannot None or empty.)rM   rV   rW   rX   )r   r#   tagr   )r,   rV   rW   rX   rU   r0   r0   r1   rZ      s   
zRepository.tagc                 C   s$   |  ||| | jj| j|d dS )zCreate tag and push to remote

        Args:
            tag_name (str): The name of the tag
            message (str): The tag message.
            ref (str, optional): The tag ref, can be commit id or branch. Defaults to MASTER_MODEL_BRANCH.
        )rM   rV   N)rZ   r#   Zpush_tagr   )r,   rV   rW   rX   r0   r0   r1   tag_and_push   s   zRepository.tag_and_push)r;   r<   )__name__
__module____qualname____doc__r   rP   r   r2   r%   r'   r>   rB   rQ   rT   r   rZ   r[   r0   r0   r0   r1   r      s`    
;	
-
r   c                   @   s   e Zd ZdZeddfdededee dee dee f
dd	Zd
efddZedfdedee dee	 fddZ
dd Zdd ZdS )DatasetRepositoryzEA local representation of the dataset (metadata) git repository.
    Nrepo_work_dir
dataset_idr   r   r   c                 C   s   || _ |r
t|tsd}t||d| _| jsd}t|tj| j| _	tj
| j| _|s7d}t||| _ddlm} |rF|| _n| | _t|| _tj| jdd | j|d	| _d
S )au  
        Instantiate a Dataset Repository object by cloning the remote ModelScope dataset repo

        Args:
            repo_work_dir (str): The dataset repo root directory.
            dataset_id (str): dataset id in ModelScope from which git clone
            revision (str, optional): revision of the dataset you want to clone from.
                                      Can be any of a branch, tag or commit hash
            auth_token (str, optional): token obtained when calling `HubApi.login()`.
                                        Usually you can safely ignore the parameter as the token is
                                        already saved when you login the first time, if None, we will use saved token.
            git_path (str, optional): The git command line path, if None, we use 'git'

        Raises:
            InvalidParameter: parameter invalid.
        z"dataset_work_dir must be provided!r3   z%dataset_work_dir can not be root dir!r   r   r   Tr   )rb   N)rb   rO   rP   r   rstripra   r   r   r   repo_base_dirr   	repo_namer   r   r   r   r    r   r#   r$   _get_repo_urlrepo_url)r,   ra   rb   r   r   r   r-   r   r0   r0   r1   r2      s*   

zDatasetRepository.__init__returnc                 C   sh   t | jr|  }| j|}|r|| jkrdS td	| j | j
| j| j| j| j| j | jS )NrY   zCloning repo from {} )r   r&   ra   r'   r#   r(   rg   r!   infoformatr)   rd   r   re   r   )r,   r/   r0   r0   r1   r)      s   zDatasetRepository.cloneFrC   r=   rF   c                 C   s   |du s	t |tsd}t|t |tstd| jstd| j| j| j | j	| j
| j |  }| j|}| j| j | jj| jdd | j| j| | jj| j| j|||d dS )a  Push local files to remote, this method will do.
           git pull
           git add
           git commit
           git push

        Args:
            commit_message (str): commit message
            branch (str, optional): which branch to push.
            force (bool, optional): whether to use forced-push.

        Raises:
            InvalidParameter: no commit message.
            NotLoginException: no access token.
        NrG   rH   rI   TrJ   rL   )rO   rP   r   rQ   r   r   r#   r+   ra   r*   rd   re   r'   r(   r>   rR   rS   rT   )r,   rC   r=   rF   rU   r/   r0   r0   r1   rT     s*   

zDatasetRepository.pushc                 C   s   t   d| dS )Nz
/datasets/r4   r   )r,   rb   r0   r0   r1   rf   1  s   zDatasetRepository._get_repo_urlc                 C   r5   r6   )r#   r7   ra   r   r8   r0   r0   r1   r'   4  r:   z!DatasetRepository._get_remote_url)r\   r]   r^   r_   r   rP   r   r2   r)   rQ   rT   rf   r'   r0   r0   r0   r1   r`      s8    
/
-r`   )r   typingr   Zmodelscope.hub.errorsr   r   r   Zmodelscope.utils.constantr   r   r   Zmodelscope.utils.loggerr	   gitr   Zutils.utilsr   r!   r   r`   r0   r0   r0   r1   <module>   s    3