Advertisement
stuppid_bot

VkClient класс для работы с API Вконтакте

Mar 30th, 2014
230
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 4.58 KB | None | 0 0
  1. # -*- coding: utf8 -*-
  2. # Модуль для работы с API Вконтакте. Список методов API можно увидеть здесь https://vk.com/dev/methods.
  3. #
  4. # @author tz4678@gmail.com
  5. import os, re, sys, json, time, uuid, urllib, urllib2, mimetypes, webbrowser
  6.  
  7. class VKClientError(Exception):
  8.     pass
  9.  
  10. class VKClient(object):
  11.     def __init__(self, api_version, access_token='', user_id=None, expires=None):
  12.         self.user_agent = 'VKClient (Python %s.%s.%s)' % sys.version_info[:3]
  13.         self.auth_url = 'https://oauth.vk.com/{0}?{1}'
  14.         self.api_url = 'https://api.vk.com/method/'
  15.         self.api_version = api_version
  16.         self.access_token = access_token
  17.         self.user_id = user_id
  18.         self.expires = expires
  19.  
  20.     def fetch_json(self, url, data=None, headers={}):
  21.         headers.setdefault('User-Agent', self.user_agent)
  22.         request = urllib2.Request(url, data, headers)
  23.         try:
  24.             response = urllib2.urlopen(request)
  25.             content = response.read()
  26.         except urllib2.HTTPError, error:
  27.             content = error.read()
  28.         return json.loads(content.decode('utf8'))
  29.  
  30.     def captcha_handler(self, url):
  31.         raise VKClientError('Captcha is needed')
  32.  
  33.     def captcha_params(self, params, response):
  34.         params['captcha_key'] = self.captcha_handler(response['captcha_img'])
  35.         params['captcha_sid'] = response['captcha_sid']
  36.  
  37.     def encode_params(self, params):
  38.         for k, v in params.items():
  39.             if type(v) == unicode:
  40.                 params[k] = v.encode('utf8')
  41.  
  42.     def auth(self, params, auth_type='authorize'):
  43.         params['v'] = self.api_version
  44.         self.encode_params(params)
  45.         response = self.fetch_json(self.auth_url.format(auth_type, urllib.urlencode(params)))
  46.         if 'error' in response:
  47.             if response['error'] == 'need_captcha':
  48.                 self.captcha_params(params, response)
  49.                 return self.auth(params)
  50.             if response['error'] == 'need_validation' and 'redirect_uri' in response:
  51.                 webbrowser.open(response['redirect_uri'])
  52.             raise VKClientError(response['error'] + ': ' + response['error_description'])
  53.         self.access_token = response['access_token']
  54.         if 'user_id' in response:
  55.             self.user_id = response['user_id']
  56.         if 'expires_in' in response and response['expires_in'] > 0:
  57.             self.expires = time.time() + response['expires_in']
  58.  
  59.     def api(self, method, params={}):      
  60.         params['v'] = self.api_version
  61.         if self.access_token:
  62.             params['access_token'] = self.access_token
  63.         self.encode_params(params)
  64.         data = urllib.urlencode(params)
  65.         headers = {'Content-Type': 'application/x-www-form-urlencoded'}
  66.         response = self.fetch_json(self.api_url + method, data, headers)
  67.         if 'error' in response:
  68.             response = response['error']
  69.             if response['error_code'] == 14:
  70.                 self.captcha_params(params, response)
  71.                 return self.api(method, params)
  72.             raise VKClientError('API error code: %s - %s' % (response['error_code'], response['error_msg']))
  73.         return response['response']
  74.  
  75.     def upload(self, upload_url, files):
  76.         boundary = '--VKClientBoundary_' + uuid.uuid4().hex
  77.         data = []
  78.         for q, w in files.items():
  79.             if re.match('https?://', w, re.I):
  80.                 u = urllib.urlopen(w)
  81.                 content_type = u.info()['content-type']
  82.                 content = u.read()
  83.             else:
  84.                 w = w.encode(sys.getfilesystemencoding())
  85.                 extension = os.path.splitext(w)[1]
  86.                 content_type = mimetypes.types_map[extension] if extension in mimetypes.types_map else 'application/octet-stream'
  87.                 f = open(w, 'rb')
  88.                 content = f.read()
  89.                 f.close()
  90.             data.extend([
  91.                 '--' + boundary,
  92.                 'Content-Disposition: form-data; name="' + q + '"; filename="' + os.path.basename(w) + '"',
  93.                 'Content-Type: ' + content_type,
  94.                 '',
  95.                 content
  96.             ])
  97.         data.extend([
  98.             '--' + boundary + '--',
  99.             ''
  100.         ])
  101.         headers = {'Content-Type': 'multipart/form-data; boundary="' + boundary + '"'}
  102.         data = '\r\n'.join(data)
  103.         response = self.fetch_json(upload_url, data, headers)
  104.         if 'error' in response:
  105.             raise VKClientError('Upload error: ' + response['error'])
  106.         return response
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement