def logger(self) -> Logger: """get the default logger of plugin which will automaticly log info into the plugin cache dir Returns: Logger: Instance of Logger Examples: ding_dong_plugin = DingDongPlugin() ding_dong_plugin.logger.info('log info ...') """ if self._default_logger: return self._default_logger self._default_logger = get_logger(self.name, file=os.path.join( self.cache_dir, 'log.log')) assert self._default_logger is not None, 'can not set default logger' return self._default_logger
EventLoginPayload, EventFriendshipPayload, EventHeartbeatPayload, EventErrorPayload, FileBox, RoomMemberPayload, RoomPayload, RoomInvitationPayload, RoomQueryFilter, FriendshipPayload, ContactPayload, MessagePayload, MessageQueryFilter, ImageType, EventType, MessageType, Puppet, PuppetOptions, MiniProgramPayload, UrlLinkPayload, get_logger) from wechaty_puppet.exceptions import ( # type: ignore WechatyPuppetConfigurationError, WechatyPuppetError, WechatyPuppetGrpcError, WechatyPuppetOperationError, WechatyPuppetPayloadError) from wechaty_puppet_official_account import config from .official_account import OfficialAccount, OfficialAccountOption from .schema import OAMessagePayload logger = get_logger('OfficialAccountPuppet') @dataclass class OfficialAccountPuppetOptions(PuppetOptions): app_id: Optional[str] = None app_secret: Optional[str] = None port: Optional[int] = 80 class OfficialAccountPuppet(Puppet): def __init__(self, options: Optional[OfficialAccountPuppetOptions]): if not options: options = OfficialAccountPuppetOptions( app_id=config.app_id, app_secret=config.app_secret,
from typing import (Union, Optional, TYPE_CHECKING) import json from wechaty.exceptions import WechatyOperationError from wechaty_puppet import ( # type: ignore FriendshipType, FriendshipPayload, get_logger) # from wechaty.utils import type_check from ..types import Acceptable from ..accessory import Accessory if TYPE_CHECKING: from .contact import Contact log = get_logger('FriendShip') class Friendship(Accessory, Acceptable): """ Send, receive friend request, and friend confirmation events. * 1. send request * 2. receive request(in friend event) * 3. confirmation friendship(friend event) """ Type = FriendshipType def __init__(self, friendship_id: str): """
from .exceptions import ( WechatyPluginError, ) if TYPE_CHECKING: from .wechaty import ( Wechaty ) from .user import ( Room, RoomInvitation, Friendship, Contact, Message, ) log: logging.Logger = get_logger(__name__) @dataclass class WechatyPluginOptions: """options for wechaty plugin""" name: Optional[str] = None metadata: Optional[dict] = None class PluginStatus(Enum): """plugin running status""" Running = 0 Stopped = 1
from .user import ( Contact, Friendship, Message, Tag, Room, Image, RoomInvitation, MiniProgram, Favorite ) from .utils import ( qr_terminal ) log = get_logger('Wechaty') DEFAULT_TIMEOUT = 300 PuppetModuleName = str @dataclass class WechatyOptions: """ WechatyOptions instance """ name: Optional[str] = None puppet: Optional[Union[PuppetModuleName, Puppet]] = None puppet_options: Optional[PuppetOptions] = None
import logging import os from typing import Optional, Union from apscheduler.schedulers.asyncio import AsyncIOScheduler from wechaty import Wechaty, Contact, UrlLink from wechaty.user import Message, Room from wechaty_puppet import ScanStatus, get_logger, FileBox # type: ignore from service.msg_service import get_wx_public_article_url_link, get_weather_url_link, get_music_file_url, \ get_south_north_fund """ 微信机器人 """ log: logging.Logger = get_logger('MyBot') class MyBot(Wechaty): """ listen wechaty event with inherited functions, which is more friendly for oop developer """ def __init__(self): super().__init__() global contact_ids global room_ids contact_ids = ['wxid_zs0tjy7p1jl922'] room_ids = ["9680172400@chatroom"] async def on_message(self, msg: Message):
See the License for the specific language governing permissions and limitations under the License. """ from __future__ import annotations from typing import ( TYPE_CHECKING, Any, List, ) from wechaty_puppet import get_logger if TYPE_CHECKING: from .tag import Tag log = get_logger('Favorite') # pylint: disable=R class Favorite: """ favorite object which handle the url_link content """ def __init__(self, favorite_id: str): self.favorite_id = favorite_id def get_id(self) -> str: """ get favorite_id :return: """
distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. """ from __future__ import annotations from typing import ( Type, ) from wechaty_puppet import ( # type: ignore FileBox, ImageType, get_logger) from ..accessory import Accessory log = get_logger('Image') class Image(Accessory): """ User Image class """ def __str__(self): return 'Image<%d>' % self.image_id def __init__( self, image_id: str, ) -> None: """ :param image_id:
you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an 'AS IS' BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. """ import os # TODO: need to fix error -> found module but no type hints or library stubs from wechaty_puppet import get_logger # type: ignore logger = get_logger('WechatyPuppetServiceConfig') def get_token(): """ get the token from environment variable """ return os.environ.get('WECHATY_PUPPET_SERVICE_TOKEN', None) or \ os.environ.get('TOKEN', None) or \ os.environ.get('token', None) or None def get_endpoint(): """ get the endpoint from environment variable """
get_logger, EventMessagePayload) from wechaty_puppet.schemas.types import ( # type: ignore MessagePayload, ContactPayload, FriendshipPayload, ImageType, RoomInvitationPayload, RoomPayload, RoomMemberPayload ) from wechaty_puppet_mock.exceptions import WechatyPuppetMockError from wechaty_puppet_mock.mock.mocker import Mocker, MockerResponse log = get_logger('PuppetMock') @dataclass class PuppetMockOptions(PuppetOptions): """options for puppet mock""" mocker: Optional[Mocker] = None # pylint: disable=too-many-public-methods class PuppetMock(Puppet): """mock for puppet""" def __init__(self, options: PuppetMockOptions, name: str = 'puppet-mock'): super().__init__(options, name) if not options.mocker:
#!/usr/bin/python # -*- coding:utf-8 -*- """plugin of groupchat assistant, including tagging, member manager, help system and timed task plugin""" from wechaty import Wechaty from wechaty.plugin import WechatyPlugin from wechaty_puppet import get_logger from tagging_plugin import Tagging from timed_task_plugin import TimedTask from member_manager_plugin import MemberManager from help_plugin import HelpSystem from help_modules.example_dict import groupchat_bot_help_zh log = get_logger('Groupchat Assistant') class GroupchatAssistant(WechatyPlugin): """groupchat assistant plugin""" @property def name(self) -> str: """get the name of plugin""" return 'groupchat assistant' def __init__(self, data_path='database.db', config_path='config.pkl'): """params: data_path: path of database file, config_path: path of database config file, which contains auto-created information""" self.plugins = [ Tagging(data_path, config_path),
import re from typing import Union import pickle from wechaty import Message, Contact, Room from wechaty.plugin import WechatyPlugin from wechaty_puppet import get_logger from data.database import Database from data.data_transfer import DataTransfer from tagging_modules.question_answering import QuestionAnswering from tagging_modules.tag_controller import TagController from tagging_modules.display import Display from utils.extract_msg import split_quote_and_mention log = get_logger('Tagging plugin') class Tagging(WechatyPlugin): """tagging system plugin for bot""" @property def name(self) -> str: """get the name of the plugin""" return 'tagging' def __init__(self, data_path='database.db', config_path='config.pkl'): """params: data_path: path of database file, config_path: path of database config file, which contains auto-created information""" self.data_path = data_path
limitations under the License. """ from __future__ import annotations from typing import TYPE_CHECKING from dataclasses import asdict from wechaty import Accessory from wechaty_puppet import MiniProgramPayload, get_logger # type: ignore from wechaty.utils import default_str if TYPE_CHECKING: from wechaty.user import Message log = get_logger('MiniProgram') class MiniProgram(Accessory): """ mini_program object which handle the url_link content """ def __init__(self, payload: MiniProgramPayload): """ initialization for mini_program :param payload: """ log.info('MiniProgram created') self._payload: MiniProgramPayload = payload @classmethod
import json from datetime import datetime from dataclasses import dataclass from wechaty_puppet import ( # type: ignore ContactPayload, RoomPayload, MessagePayload, Puppet, get_logger, EventType, FileBox, MessageType) from wechaty import ( # type: ignore Contact, Room, Message) if TYPE_CHECKING: from wechaty import Contact, Wechaty from wechaty_puppet_mock.mock.environment import EnvironmentMock from wechaty_puppet_mock.exceptions import WechatyPuppetMockError log = get_logger('Mocker') @dataclass class MockerResponse: """this is the common data-structure for mocker""" type: int payload: str class Mocker(AsyncIOEventEmitter): """mock fake data""" def __init__(self): super().__init__() self.id: str = str(uuid4())
EventType, MessageType, Puppet, PuppetOptions, MiniProgramPayload, UrlLinkPayload, get_logger ) from .config import ( WECHATY_PUPPET_PADPLUS_ENDPOINT, WECHATY_PUPPET_PADPLUS_TOKEN ) log = get_logger('PadPlusPuppet') def _map_message_type(message_payload: MessagePayload) -> MessagePayload: """ get messageType value which is ts-wechaty-puppet type from hostie server, but is MessageType. so we should map it to MessageType from chatie-grpc target MessageType Enum: MESSAGE_TYPE_UNSPECIFIED = 0; MESSAGE_TYPE_ATTACHMENT = 1; MESSAGE_TYPE_AUDIO = 2; MESSAGE_TYPE_CONTACT = 3; MESSAGE_TYPE_EMOTICON = 4; MESSAGE_TYPE_IMAGE = 5; MESSAGE_TYPE_TEXT = 6;
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an 'AS IS' BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. """ import os import re from typing import ( Optional, ) from wechaty_puppet import ( # type: ignore FileBox, get_logger) log = get_logger('Config') # log.debug('test logging debug') # log.info('test logging info') _FILE_PATH = os.path.dirname(os.path.realpath(__file__)) DATA_PATH = os.path.realpath(os.path.join( _FILE_PATH, '../data', ), ) def global_exception_handler(exception: Exception) -> None: """ handle the global exception :param exception: exception message
from wechaty_puppet.watch_dog import WatchdogFood, Watchdog # type: ignore from .utils import (qr_terminal) from .user import (Contact, Friendship, Message, Tag, Room, Image, RoomInvitation, MiniProgram, Favorite, ContactSelf) from .plugin import (WechatyPlugin, WechatyPluginManager) from .exceptions import ( # type: ignore WechatyStatusError, WechatyConfigurationError, WechatyOperationError, ) from .utils import timestamp_to_date log: logging.Logger = get_logger('Wechaty') DEFAULT_TIMEOUT = 300 PuppetModuleName = str @dataclass class WechatyOptions: """ WechatyOptions instance """ name: Optional[str] = None puppet: Optional[Union[PuppetModuleName, Puppet]] = None puppet_options: Optional[PuppetOptions] = None
MatcherOption, RoomMatcher, MessageMatcher, ContactMatcher) from wechaty_plugin_contrib.exception import (WechatyPluginConfigurationError) @dataclass class RoomInviterOptions(WechatyPluginOptions): # add rules to the specific Matcher rules: Dict[MessageMatcher, Union[List[RoomMatcher], RoomMatcher]] = field(default_factory=dict) welcome: str = field(default_factory=str) logger = get_logger('RoomInviterPlugin') class RoomInviterPlugin(WechatyPlugin): def __init__(self, options: RoomInviterOptions): super().__init__(options) if not options or not options.rules: raise ValueError('options is required, please add matcher rules') self.rules: Dict[MessageMatcher, List[RoomMatcher]] = {} for matcher, room_obj in options.rules.items(): if not room_obj: raise ValueError( f'matcher<{matcher}> can not match the target room') if isinstance(room_obj, RoomMatcher): self.rules[matcher] = [room_obj]
FileBox, MessagePayload, MessageQueryFilter, MessageType, get_logger) from wechaty.exceptions import WechatyPayloadError, WechatyOperationError from wechaty.utils import timestamp_to_date from ..accessory import Accessory from .mini_program import MiniProgram # TODO -> remove Sayable interface temporary # from ..types import Sayable from .contact import Contact from .url_link import UrlLink from .image import Image from .room import Room log = get_logger('Message') SUPPORTED_MESSAGE_FILE_TYPES: List[MessageType] = [ MessageType.MESSAGE_TYPE_ATTACHMENT, MessageType.MESSAGE_TYPE_EMOTICON, MessageType.MESSAGE_TYPE_IMAGE, MessageType.MESSAGE_TYPE_VIDEO, MessageType.MESSAGE_TYPE_AUDIO ] # pylint: disable=R0904,R0903 class Message(Accessory[MessagePayload]): """ All of wechaty messages will be encapsulated as a Message object. you can get all of message attribute through publish method. """
distributed under the License is distributed on an 'AS IS' BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. """ from __future__ import annotations from typing import Union, List import json from datetime import datetime from wechaty_puppet import RoomInvitationPayload, get_logger # type: ignore from .contact import Contact from ..types import Acceptable from ..accessory import Accessory log = get_logger('RoomInvitation') class RoomInvitation(Accessory, Acceptable): """ Room Invitation """ def __init__(self, room_invitation_id: str): """ initialization """ if self.puppet is None: raise Exception( 'RoomInvitation class can not be instanciated directly!') self.invitation_id: str = room_invitation_id log.info('__init__ () <%s>', self)
TypeVar, Generic, ) from wechaty_puppet import ( get_logger, Puppet, ) from wechaty.exceptions import WechatyAccessoryBindingError # pylint:disable=R0401 if TYPE_CHECKING: from .wechaty import Wechaty log = get_logger('Accessory') PayloadType = TypeVar('PayloadType') class Accessory(Generic[PayloadType]): """ Translate the function from TypeScript to Python See: https://github.com/wechaty/wechaty/blob/master/src/accessory.ts """ _puppet: Optional[Puppet] = None _wechaty: Optional[Wechaty] = None abstract: bool = True
""" UrlLink for Contact Message """ from __future__ import annotations from typing import ( Type, Union ) import requests from lxml import etree # type: ignore from wechaty_puppet import UrlLinkPayload, get_logger # type: ignore log = get_logger('UrlLink') class UrlLink: """ url_link object which handle the url_link content """ def __init__( self, payload: UrlLinkPayload, ): """ initialization :param payload: """ self.payload: UrlLinkPayload = payload
from typing import Any, Optional from dataclasses import dataclass from diskcache import Cache from wechaty_puppet import (get_logger, WechatyPuppetOperationError) from .schema import (OAMessagePayload, OAContactPayload, AccessTokenPayload) @dataclass class DataStoreOption: cache_dir: str = os.path.join(os.getcwd(), '.wechaty', 'wechaty-puppet-official-account', 'data_cache') logger = get_logger('DataStore') class DataStore: """ store the payload with domain """ def __init__(self, option: Optional[DataStoreOption] = None): """init the payload directory""" if not option: option = DataStoreOption() logger.info(f'init DataStore instance <{option}>') self.option: DataStoreOption = option if not os.path.exists(self.option.cache_dir):
EventHeartbeatPayload, EventReadyPayload, ScanStatus) from .exceptions import ( WechatyPluginError, ) if TYPE_CHECKING: from .wechaty import (Wechaty) from .user import ( Room, RoomInvitation, Friendship, Contact, Message, ) log: Logger = get_logger(__name__) def _check_local_port(port: int) -> bool: """ check if the local port is in use Args: port (int): port Return: return True if the local port is valid, otherwise False Examples: >>> assert _check_local_port(5000) """
from pyee import AsyncIOEventEmitter # type: ignore # from wechaty_puppet import RoomMemberPayload from wechaty.exceptions import WechatyOperationError, WechatyPayloadError from wechaty_puppet import ( # type: ignore FileBox, RoomQueryFilter, RoomMemberQueryFilter, RoomPayload, get_logger) # from wechaty.utils import type_check from ..accessory import Accessory from ..config import AT_SEPARATOR if TYPE_CHECKING: from .contact import Contact from .url_link import UrlLink from .mini_program import MiniProgram from .message import Message log = get_logger('Room') class Room(Accessory[RoomPayload]): """ All wechat rooms(groups) will be encapsulated as a Room. """ _pool: Dict[str, 'Room'] = defaultdict() def __init__(self, room_id: str) -> None: """docs""" super().__init__() self.room_id = room_id _event_stream: AsyncIOEventEmitter = AsyncIOEventEmitter()
from typing import ( Dict, # Optional, Union, TYPE_CHECKING) from collections import defaultdict from wechaty_puppet import get_logger # type: ignore from ..accessory import ( Accessory, ) if TYPE_CHECKING: from .contact import Contact from .favorite import Favorite log = get_logger('Tag') class Tag(Accessory): """ tag object which handle the url_link content """ _pool: Dict[str, 'Tag'] = defaultdict() tag_id: str def __init__( self, tag_id: str, ) -> None: """
""" config unit test """ from typing import ( Any, # Dict, Iterable, ) from wechaty_puppet import get_logger # type: ignore import pytest # type: ignore # pylint: disable=C0103 log = get_logger('ConfigTest') # pylint: disable=redefined-outer-name # https://stackoverflow.com/a/57015304/1123955 @pytest.fixture(name='data', scope='module') def fixture_data() -> Iterable[str]: """ doc """ yield 'test' def test_config(data: Any, ) -> None: """ Unit Test for config function """ print(data)
class AutoReplyRule: keyword: str reply_content: Union[str, FileBox, Contact, Message, MiniProgram] @dataclass class AutoReplyOptions(WechatyPluginOptions): rules: List[AutoReplyRule] = field(default_factory=list) matchers: List[Matcher] = field(default_factory=list) # add rules to the specific Matcher matcher_rules: Dict[Matcher, List[AutoReplyRule]] = field(default_factory=dict) logger = get_logger('AutoReplyPlugin') class AutoReplyPlugin(WechatyPlugin): def __init__(self, options: AutoReplyOptions): super().__init__(options) if not options.rules and not options.matcher_rules.values(): raise WechatyPluginConfigurationError( 'rules not found in rules/matcher_rules') # if there is no matcher, it should be apply to all of target if not options.matchers: options.matchers = [ RoomMatcher(True), MessageMatcher(True),
from wechaty.config import PARALLEL_TASK_NUM from wechaty.utils.async_helper import gather_with_concurrency from ..accessory import Accessory if TYPE_CHECKING: # pytype: disable=pyi-error from .tag import Tag # pytype: disable=pyi-error from .message import Message # pytype: disable=pyi-error from .url_link import UrlLink from .mini_program import MiniProgram log = get_logger('Contact') # pylint:disable=R0904 class Contact(Accessory[ContactPayload], AsyncIOEventEmitter): """ contact object """ _pool: Dict[str, 'Contact'] = {} def __init__(self, contact_id: str): """ Init Contact object with id which will not be cached, so we suggest that you use load method to get a cached contact object
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an 'AS IS' BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. """ from __future__ import annotations import os import asyncio from typing import List, Optional from wechaty import Wechaty, Room, RoomQueryFilter from wechaty.user.contact import Contact from wechaty_puppet import get_logger log = get_logger('RoomMemberBot') class MyBot(Wechaty): """oop wechaty bot, all of your entrypoint should be done here. """ async def on_ready(self, payload): """all of initialization jobs shoule be done here. """ log.info('ready event<%s>', payload) # search contact and add them to the specific room room: Optional[Room] = await self.Room.find(query=RoomQueryFilter(topic='room-topic-name')) if not room: return contacts: List[Contact] = await self.Contact.find_all()