Skip to content

Commit 7c3ba9b

Browse files
author
Stefan Oderbolz
committed
Move to subdirectory and add examples
1 parent 55351d4 commit 7c3ba9b

9 files changed

+200
-0
lines changed

README.md

+4
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
swissparlpy
2+
===========
3+
4+
Inspired by the R package swissparl, this module provides easy access to the data of the webservice of the Swiss parliament.

examples/filter.py

+12
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
import swissparlpy as spp
2+
from pprint import pprint
3+
4+
subjects = spp.get_data(
5+
table="SubjectBusiness",
6+
BusinessShortNumber="05.057",
7+
Language="DE"
8+
)
9+
10+
print(f"Total rows: {len(subjects)}")
11+
for subject in subjects:
12+
pprint(subject)

examples/glimpse.py

+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
import swissparlpy
2+
3+
glimpse = swissparlpy.get_glimpse("Canton", 10)
4+
for r in glimpse:
5+
print(r)
6+
+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
import swissparlpy
2+
3+
# print all tables with their properties
4+
5+
overview = swissparlpy.get_overview()
6+
for table, props in overview.items():
7+
print(table)
8+
for prop in props:
9+
print(f' + {prop}')
10+
print('')

examples/slice.py

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
import swissparlpy as spp
2+
from pprint import pprint
3+
4+
subjects = spp.get_data(
5+
table="Voting",
6+
)
7+
8+
print(f"Total rows: {len(subjects)}")
9+
for subject in subjects[5:10]:
10+
pprint(subject)

setup.py

+43
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
# -*- coding: utf-8 -*-
2+
3+
from codecs import open
4+
from setuptools import setup, find_packages
5+
import re
6+
7+
with open('swissparlpy/__init__.py', 'r') as fd:
8+
version = re.search(r'^__version__\s*=\s*[\'"]([^\'"]*)[\'"]',
9+
fd.read(), re.MULTILINE).group(1)
10+
11+
if not version:
12+
raise RuntimeError('Cannot find version information')
13+
14+
with open('README.md', 'r', encoding="utf-8") as f:
15+
long_description = f.read()
16+
17+
setup(
18+
name='swissparlpy',
19+
packages=find_packages(),
20+
version=version,
21+
install_requires=['requests', 'pyodata'],
22+
description='Client for Swiss parliament API',
23+
long_description=long_description,
24+
long_description_content_type='text/markdown',
25+
author='Stefan Oderbolz',
26+
author_email='odi@metaodi.ch',
27+
maintainer='Stefan Oderbolz',
28+
maintainer_email='odi@metaodi.ch',
29+
url='https://github.com/metaodi/swissparlpy',
30+
download_url='https://github.com/metaodi/swissparlpy/archive/v%s.zip' % version,
31+
keywords=['api', 'swiss', 'switzerland', 'parliament', 'odata', 'swissparl'],
32+
license='MIT',
33+
classifiers=[
34+
'License :: OSI Approved :: MIT License',
35+
'Intended Audience :: Developers',
36+
'Topic :: Software Development :: Libraries',
37+
'Development Status :: 4 - Beta',
38+
'Programming Language :: Python :: 3.6',
39+
'Programming Language :: Python :: 3.7',
40+
'Programming Language :: Python :: 3.8',
41+
],
42+
python_requires='>=3.6'
43+
)

swissparlpy/__init__.py

+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
__version__ = '0.0.1'
2+
__all__ = ['client', 'errors']
3+
4+
from .errors import SwissParlError
5+
from .client import SwissParlClient
6+
7+
def get_tables():
8+
client = SwissParlClient()
9+
return client.get_tables()
10+
11+
def get_variables(table):
12+
client = SwissParlClient()
13+
return client.get_variables()
14+
15+
def get_overview():
16+
client = SwissParlClient()
17+
return client.get_overview()
18+
19+
def get_glimpse(table, rows=5):
20+
client = SwissParlClient()
21+
return client.get_glimpse(table, rows)
22+
23+
def get_data(table, **kwargs):
24+
client = SwissParlClient()
25+
return client.get_data(table, **kwargs)

swissparlpy/client.py

+86
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
import requests
2+
import pyodata
3+
4+
SERVICE_URL = 'https://ws.parlament.ch/odata.svc/'
5+
6+
7+
class SwissParlClient(object):
8+
def __init__(self, session=None):
9+
if not session:
10+
session = requests.Session()
11+
self.client = pyodata.Client(SERVICE_URL, session)
12+
self.cache = {}
13+
self.get_overview()
14+
15+
def get_tables(self):
16+
if self.cache:
17+
return self.cache.keys()
18+
return [es.name for es in self.client.schema.entity_sets]
19+
20+
def get_variables(self, table):
21+
if self.cache and table in self.cache:
22+
return self.cache[table]
23+
return [p.name for p in self.client.schema.entity_type(table).proprties()]
24+
25+
def get_overview(self):
26+
if self.cache:
27+
return self.cache
28+
self.cache = {}
29+
for t in self.get_tables():
30+
self.cache[t] = self.get_variables(t)
31+
return self.cache
32+
33+
def get_glimpse(self, table, rows=5):
34+
entities = self._get_entities(table)
35+
return SwissParlResponse(
36+
entities.top(rows).count(inline=True),
37+
self.get_variables(table)
38+
)
39+
40+
def get_data(self, table, **kwargs):
41+
entities = self._get_entities(table)
42+
return SwissParlResponse(
43+
entities.count(inline=True).filter(**kwargs),
44+
self.get_variables(table)
45+
)
46+
47+
def _get_entities(self, table):
48+
return getattr(self.client.entity_sets, table).get_entities()
49+
50+
51+
class SwissParlResponse(object):
52+
def __init__(self, entity_request, variables):
53+
self.entities = entity_request.execute()
54+
self.count = self.entities.total_count
55+
self.variables = variables
56+
57+
self.data = []
58+
self._setup_proxies()
59+
60+
61+
def _setup_proxies(self):
62+
for e in self.entities:
63+
row = {k: SwissParlDataProxy(e, k) for k in self.variables}
64+
self.data.append(row)
65+
66+
def __len__(self):
67+
return self.count
68+
69+
def __iter__(self):
70+
for row in self.data:
71+
yield {k: v() for k,v in row.items()}
72+
73+
def __getitem__(self, key):
74+
items = self.data[key]
75+
if isinstance(key, slice):
76+
return [{k: v() for k,v in i.items()} for i in items]
77+
return {k: v() for k,v in items.items()}
78+
79+
80+
class SwissParlDataProxy(object):
81+
def __init__(self, proxy, attribute):
82+
self.proxy = proxy
83+
self.attribute = attribute
84+
85+
def __call__(self):
86+
return getattr(self.proxy, self.attribute)

swissparlpy/errors.py

+4
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
class SwissParlError(Exception):
2+
"""
3+
General SwissParl error class to provide a superclass for all other errors
4+
"""

0 commit comments

Comments
 (0)